// ARGUS Beta — terminal.chat.js (Faz D: "Uygulama modu" / chat-bubble wrapper)
//
// A chat-style overlay on top of the real terminal. The xterm terminal keeps running
// the real PTY underneath; this layer:
//   - takes input as chat messages (textarea + send) and writes them to the PTY,
//   - mirrors PTY output into assistant bubbles after stripping ANSI/control noise,
//   - is chosen per-connection via a "Terminal / Uygulama" toggle on the launcher,
//   - can always be dismissed with "Terminali Göster" to fall back to raw xterm.
//
// Reaches the terminal through window.__argusTerm / __argusSend (exposed by the bundle).
// Output mirroring is best-effort: great for line-based shells, rougher for full-screen
// TUIs (Claude Code/Codex redraw the whole screen). The raw terminal is always one tap away.
(function () {
  "use strict";

  var MODE_KEY = "argus.connMode"; // 'terminal' | 'app'
  function getMode() { try { return localStorage.getItem(MODE_KEY) || "terminal"; } catch (_) { return "terminal"; } }
  function setMode(m) { try { localStorage.setItem(MODE_KEY, m); } catch (_) {} }

  var term = null, root = null, msgsEl = null, inputEl = null, titleEl = null;
  var pending = null, idleT = 0, capturing = false, hooked = false, active = false, lastSent = "";
  function escapeRe(s) { return s.replace(/[.*+?^${}()|[\]\\]/g, "\\$&"); }

  // ---------------- ANSI / control cleanup ----------------
  function clean(s) {
    s = s.replace(/\x1b\][^\x07\x1b]*(?:\x07|\x1b\\)/g, "");      // OSC … BEL/ST
    s = s.replace(/\x1b\[[0-9;?]*[ -\/]*[@-~]/g, "");             // CSI … final
    s = s.replace(/\x1b[()#][0-9A-Za-z]/g, "");                    // charset designators
    s = s.replace(/\x1b[=>78MNODEc]/g, "");                        // misc single escapes
    s = s.replace(/[^\n]*\r(?!\n)/g, "");                          // collapse \r overwrites (spinners)
    s = s.replace(/[\x00-\x08\x0b\x0c\x0e-\x1f\x7f]/g, "");        // stray control chars (keep \n,\t)
    return s;
  }
  function decode(u8) { try { return new TextDecoder().decode(u8); } catch (_) { return ""; } }

  // ---------------- output mirroring ----------------
  function hookOutput() {
    if (hooked || !term || typeof term.write !== "function") return;
    hooked = true;
    var ow = term.write.bind(term);
    term.write = function (data, cb) {
      try { if (capturing) feed(typeof data === "string" ? data : decode(data)); } catch (_) {}
      return ow(data, cb);
    };
  }
  // Mirror raw PTY bytes into an assistant bubble. We accumulate RAW and re-clean the
  // whole buffer each time so \r line-overwrites (PSReadLine syntax redraw, spinners)
  // collapse correctly instead of piling up.
  function feed(raw) {
    if (!pending) {
      if (!clean(raw).trim()) return;
      pending = startAssistant();
    }
    pending.raw += raw;
    pending.el.textContent = render(pending.raw);
    scrollBottom();
    clearTimeout(idleT);
    idleT = setTimeout(finalizeAssistant, 700);
  }
  function render(raw) {
    var t = clean(raw).replace(/\n{3,}/g, "\n\n");
    if (lastSent) { // drop the leading echo of the command we just sent
      t = t.replace(new RegExp("^[ \\t]*" + escapeRe(lastSent) + "[ \\t\\r]*\\n?"), "");
    }
    return t.replace(/^\s+/, "").replace(/\s+$/, "");
  }
  function startAssistant() {
    var wrap = document.createElement("div");
    wrap.className = "ac-row ac-assistant";
    var b = document.createElement("div");
    b.className = "ac-bubble"; wrap.appendChild(b);
    msgsEl.appendChild(wrap); scrollBottom();
    return { el: b, raw: "" };
  }
  function finalizeAssistant() {
    clearTimeout(idleT);
    if (pending) {
      var txt = render(pending.raw);
      if (!txt) pending.el.parentNode.remove();
      else {
        pending.el.textContent = txt;
        if (window.ArgusEnhance && window.ArgusEnhance.notifyNative) {
          window.ArgusEnhance.notifyNative("Yanıt hazır", txt.slice(0, 90));
        }
      }
    }
    pending = null;
  }

  // ---------------- input ----------------
  function addUser(text) {
    var wrap = document.createElement("div");
    wrap.className = "ac-row ac-user";
    var b = document.createElement("div");
    b.className = "ac-bubble"; b.textContent = text;
    wrap.appendChild(b); msgsEl.appendChild(wrap); scrollBottom();
  }
  function sendMsg() {
    var v = inputEl.value;
    if (!v.trim()) return;
    finalizeAssistant();
    addUser(v);
    lastSent = v;
    if (window.__argusSend) window.__argusSend({ type: "input", data: v + "\r" });
    inputEl.value = ""; autoGrow();
    inputEl.focus();
  }
  function sendRaw(data) { if (window.__argusSend) window.__argusSend({ type: "input", data: data }); }
  function autoGrow() {
    inputEl.style.height = "auto";
    inputEl.style.height = Math.min(inputEl.scrollHeight, 120) + "px";
  }
  function scrollBottom() { if (msgsEl) msgsEl.scrollTop = msgsEl.scrollHeight; }

  // ---------------- enable / disable ----------------
  function enable(titleText) {
    if (!window.__argusTerm) return;
    term = window.__argusTerm;
    buildUI();
    hookOutput();
    if (titleText) titleEl.textContent = titleText;
    root.hidden = false; active = true; capturing = true;
    document.body.classList.add("ac-on");
    setTimeout(function () { inputEl && inputEl.focus(); }, 50);
  }
  function disable() {
    active = false; capturing = false;
    finalizeAssistant();
    if (root) root.hidden = true;
    document.body.classList.remove("ac-on");
  }

  // ---------------- UI ----------------
  function buildUI() {
    if (root) return;
    injectCSS();
    root = document.createElement("div");
    root.id = "argus-chat"; root.hidden = true;
    root.innerHTML =
      '<header class="ac-head">' +
        '<button class="ac-back" aria-label="Terminali Göster">‹</button>' +
        '<div class="ac-title">Uygulama</div>' +
        '<button class="ac-term" aria-label="Terminali Göster">⌨</button>' +
      '</header>' +
      '<div class="ac-msgs"></div>' +
      '<form class="ac-input">' +
        '<button type="button" class="ac-attach" aria-label="Foto / Dosya">＋</button>' +
        '<textarea class="ac-ta" rows="1" placeholder="mesaj yaz…" autocapitalize="sentences"></textarea>' +
        '<button type="submit" class="ac-send" aria-label="Gönder">↑</button>' +
      '</form>';
    document.body.appendChild(root);
    msgsEl = root.querySelector(".ac-msgs");
    inputEl = root.querySelector(".ac-ta");
    titleEl = root.querySelector(".ac-title");

    root.querySelector(".ac-input").addEventListener("submit", function (e) { e.preventDefault(); sendMsg(); });
    root.querySelector(".ac-send").addEventListener("click", function (e) { e.preventDefault(); sendMsg(); });
    root.querySelector(".ac-back").addEventListener("click", disable);
    root.querySelector(".ac-term").addEventListener("click", disable);
    root.querySelector(".ac-attach").addEventListener("click", function () {
      // reuse enhance.js uploader if present, else just focus
      if (window.ArgusEnhance && window.ArgusEnhance.uploadFile) window.ArgusEnhance.uploadFile(afterUpload);
    });
    inputEl.addEventListener("input", autoGrow);
    inputEl.addEventListener("keydown", function (e) {
      if (e.key === "Enter" && !e.shiftKey) { e.preventDefault(); sendMsg(); }
    });
  }
  function afterUpload(path) { if (path) { inputEl.value += (inputEl.value ? " " : "") + path + " "; autoGrow(); inputEl.focus(); } }

  function injectCSS() {
    if (document.getElementById("argus-chat-css")) return;
    var s = document.createElement("style"); s.id = "argus-chat-css";
    s.textContent = [
      "#argus-chat{position:fixed;left:0;right:0;top:var(--vvt);height:var(--vvh);z-index:60;display:flex;flex-direction:column;background:var(--bg);color:var(--text)}",
      "#argus-chat[hidden]{display:none}",
      ".ac-head{display:flex;align-items:center;gap:var(--sp-2);min-height:var(--tap);padding:var(--sat) max(var(--sp-2),var(--sar)) 0 max(var(--sp-2),var(--sal));background:var(--surface-1);border-bottom:1px solid var(--border)}",
      ".ac-back,.ac-term{flex:0 0 auto;width:var(--tap);height:var(--tap);border:0;background:transparent;color:var(--text-muted);font-size:24px;cursor:pointer;border-radius:var(--r-md)}",
      ".ac-back:active,.ac-term:active{background:var(--surface-2)}",
      ".ac-title{flex:1;text-align:center;font:var(--fw-bold) var(--fs-500)/1 var(--font-ui);letter-spacing:.02em}",
      ".ac-msgs{flex:1;min-height:0;overflow-y:auto;-webkit-overflow-scrolling:touch;padding:var(--sp-4) var(--sp-3);display:flex;flex-direction:column;gap:var(--sp-3)}",
      ".ac-row{display:flex}",
      ".ac-user{justify-content:flex-end}",
      ".ac-assistant{justify-content:flex-start}",
      ".ac-bubble{max-width:82%;padding:var(--sp-3);border-radius:var(--r-lg);font:var(--fw-medium) var(--fs-400)/var(--lh-body) var(--font-ui);white-space:pre-wrap;word-break:break-word;box-shadow:var(--shadow-1)}",
      ".ac-user .ac-bubble{background:var(--accent);color:var(--on-accent);border-bottom-right-radius:var(--r-sm)}",
      ".ac-assistant .ac-bubble{background:var(--surface-2);color:var(--text);border:1px solid var(--border);border-bottom-left-radius:var(--r-sm);font-family:var(--font-mono);font-size:var(--fs-300)}",
      ".ac-input{flex:0 0 auto;display:flex;align-items:flex-end;gap:var(--sp-2);padding:var(--sp-2) max(var(--sp-2),var(--sar)) max(var(--sp-2),var(--sab)) max(var(--sp-2),var(--sal));background:var(--surface-1);border-top:1px solid var(--border)}",
      ".ac-attach,.ac-send{flex:0 0 auto;width:42px;height:42px;border:0;border-radius:50%;cursor:pointer;font-size:22px;display:flex;align-items:center;justify-content:center}",
      ".ac-attach{background:var(--surface-2);color:var(--text-muted)}",
      ".ac-send{background:var(--accent);color:var(--on-accent);font-weight:var(--fw-bold)}",
      ".ac-attach:active{background:var(--surface-3)}.ac-send:active{filter:brightness(.92)}",
      ".ac-ta{flex:1;min-width:0;resize:none;max-height:120px;padding:var(--sp-3) var(--sp-4);border:1px solid var(--border-strong);border-radius:var(--r-lg);background:var(--surface-input);color:var(--text);font:var(--fw-medium) var(--fs-400) var(--font-ui);outline:none}",
      ".ac-ta:focus{border-color:var(--accent)}",
      ".ac-ta::placeholder{color:var(--text-faint)}"
    ].join("");
    document.head.appendChild(s);
  }

  // ---------------- launcher integration ----------------
  // Add a "Terminal / Uygulama" segmented toggle into the launcher card, and arm the
  // app overlay when a connection is started while "Uygulama" is selected.
  function decorateLauncher() {
    var launcher = document.getElementById("launcher");
    if (!launcher) return;
    var card = launcher.querySelector(".lc-card");
    if (!card || card.querySelector(".ac-modeseg")) return;
    var seg = document.createElement("div");
    seg.className = "ac-modeseg";
    seg.innerHTML =
      '<button data-m="terminal">Terminal</button>' +
      '<button data-m="app">Uygulama</button>';
    var p = card.querySelector("p");
    if (p && p.nextSibling) card.insertBefore(seg, p.nextSibling); else card.appendChild(seg);
    injectSegCSS();
    function paint() {
      var m = getMode();
      seg.querySelectorAll("button").forEach(function (b) {
        b.classList.toggle("on", b.getAttribute("data-m") === m);
      });
    }
    seg.querySelectorAll("button").forEach(function (b) {
      b.addEventListener("click", function (e) { e.stopPropagation(); setMode(b.getAttribute("data-m")); paint(); });
    });
    paint();

    // arm overlay on connection start (capture phase so we run before the bundle handler)
    launcher.querySelectorAll(".lc-btn").forEach(function (btn) {
      if (btn.__acArmed) return; btn.__acArmed = true;
      btn.addEventListener("click", function () {
        if (getMode() !== "app") return;
        var label = (btn.querySelector(".lc-l") || {}).textContent || "Uygulama";
        // wait for the session/terminal to come up, then open the chat overlay
        var n = 0, iv = setInterval(function () {
          if (window.__argusTerm && document.querySelector(".xterm-viewport")) { clearInterval(iv); enable(label); }
          else if (++n > 60) clearInterval(iv);
        }, 100);
      }, true);
    });
  }
  function injectSegCSS() {
    if (document.getElementById("argus-seg-css")) return;
    var s = document.createElement("style"); s.id = "argus-seg-css";
    s.textContent = [
      ".ac-modeseg{display:flex;gap:0;margin:0 0 var(--sp-4);border:1px solid var(--border-strong);border-radius:var(--r-md);overflow:hidden;background:var(--surface-1)}",
      ".ac-modeseg button{flex:1;appearance:none;border:0;background:transparent;color:var(--text-muted);font:var(--fw-bold) var(--fs-300)/1 var(--font-ui);padding:var(--sp-3) 0;cursor:pointer}",
      ".ac-modeseg button.on{background:var(--accent);color:var(--on-accent)}"
    ].join("");
    document.head.appendChild(s);
  }

  // watch for the launcher (re)appearing
  function watch() {
    decorateLauncher();
    var mo = new MutationObserver(decorateLauncher);
    mo.observe(document.body, { childList: true, subtree: true });
  }

  // ---------------- bootstrap ----------------
  window.ArgusChat = { enable: enable, disable: disable, getMode: getMode, setMode: setMode };
  function boot() { watch(); }
  if (document.readyState === "loading") document.addEventListener("DOMContentLoaded", boot);
  else boot();
})();
