// AdBlockMaxxer popup — counter, toggles, per-site allowlist, Twitch update notice.

const STORAGE_TOGGLES = ["ytReclaim", "youtubeSkip", "sponsorblock", "spotifyMute", "twitchPoints", "twitchExtras", "twitchGame", "cookieDismiss", "cosmetic"]; // pure storage flags (all default ON)
const UPDATE_CMD =
  'curl -fsSL https://raw.githubusercontent.com/pixeltris/TwitchAdSolutions/master/video-swap-new/video-swap-new.user.js -o vendor/video-swap-new.user.js';

let currentHost = null;

function baseDomain(hostname) {
  // crude eTLD+1: good enough for an allowlist (handles co.uk-ish with a small fudge)
  const parts = hostname.split(".");
  if (parts.length <= 2) return hostname;
  const twoLevelTlds = ["co.uk", "com.au", "co.jp", "co.nz", "com.br"];
  const last2 = parts.slice(-2).join(".");
  if (twoLevelTlds.includes(last2)) return parts.slice(-3).join(".");
  return parts.slice(-2).join(".");
}

function render() {
  chrome.storage.local.get(
    ["adsSkipped", "allowlist", "easylistEnabled", "snoozeUntil", "twitchUpdateAvailable", "twitchLocalVer", "twitchRemoteVer", "selfUpdateAvailable", "selfLocalVer", "selfRemoteVer", "selfUpdateNotes", "selfUpdateUrl", "perfMode", "twitchChatOverlay", "twitchForceQuality", "ytReclaimAlways", "ytEnforced", "sysOpen", "sysAuto", ...STORAGE_TOGGLES],
    function (data) {
      document.getElementById("count").textContent = (data.adsSkipped || 0).toLocaleString();

      STORAGE_TOGGLES.forEach(function (key) {
        const el = document.getElementById(key);
        if (el) el.checked = data[key] !== false;
      });
      document.getElementById("easylist").checked = data.easylistEnabled !== false;
      document.getElementById("perfMode").checked = data.perfMode === true; // defaults OFF
      document.getElementById("twitchChatOverlay").checked = data.twitchChatOverlay === true; // defaults OFF
      document.getElementById("twitchForceQuality").checked = data.twitchForceQuality === true; // defaults OFF
      document.getElementById("sysToggle").checked = data.sysOpen === true; // Daily Quest panel open?
      document.getElementById("sysAuto").checked = data.sysAuto !== false; // auto-summon (default ON)
      var ytAlwaysEl = document.getElementById("ytReclaimAlways");
      if (ytAlwaysEl) ytAlwaysEl.checked = data.ytReclaimAlways === true; // defaults OFF (auto mode)

      // snooze button state
      const left = (data.snoozeUntil || 0) - Date.now();
      const snoozeBtn = document.getElementById("snooze");
      const snoozeLbl = document.getElementById("snoozeLbl");
      if (left > 0) {
        snoozeLbl.textContent = "Resume (" + Math.ceil(left / 60000) + "m left)";
        snoozeBtn.classList.add("active");
      } else {
        snoozeLbl.textContent = "Snooze 5 min";
        snoozeBtn.classList.remove("active");
      }

      // allowlist state for the active site
      const allow = data.allowlist || [];
      if (currentHost) {
        const dom = baseDomain(currentHost);
        const paused = allow.some(function (d) { return currentHost === d || currentHost.endsWith("." + d); });
        // set the two spans only — never the button's textContent (that would delete the spans)
        document.getElementById("allowVerb").textContent = paused ? "Resume on" : "Pause on";
        document.getElementById("siteName").textContent = dom;
        document.getElementById("allowToggle").classList.toggle("active", paused);
      }

      // Extension self-update notice (off-store, so we detect + offer a one-click download)
      const selfNotice = document.getElementById("selfUpdateNotice");
      if (data.selfUpdateAvailable) {
        selfNotice.classList.remove("hidden");
        const notes = data.selfUpdateNotes ? " — " + data.selfUpdateNotes : "";
        document.getElementById("selfUpdateText").textContent =
          "Update available: v" + (data.selfLocalVer || "?") + " → v" + (data.selfRemoteVer || "?") + notes;
      } else {
        selfNotice.classList.add("hidden");
      }

      // YouTube server-side enforcement: paused + auto-retrying. Reflect it honestly so the
      // green "stripped" row doesn't lie when the account is actually being enforced.
      const ytNotice = document.getElementById("ytEnforcedNotice");
      const ytDot = document.getElementById("ytDot");
      const ytStatusText = document.getElementById("ytStatusText");
      if (data.ytEnforced) {
        ytNotice.classList.remove("hidden");
        if (ytDot) ytDot.classList.replace("on", "warn");
        if (ytStatusText) ytStatusText.textContent = "YouTube — ads enforced on this account (paused)";
      } else {
        ytNotice.classList.add("hidden");
        if (ytDot) ytDot.classList.replace("warn", "on");
        if (ytStatusText) ytStatusText.textContent = "YouTube — ad placements stripped";
      }

      // Twitch update notice
      const notice = document.getElementById("updateNotice");
      if (data.twitchUpdateAvailable) {
        notice.classList.remove("hidden");
        document.getElementById("updateText").textContent =
          "Twitch fix update: v" + (data.twitchLocalVer || "?") + " → v" + (data.twitchRemoteVer || "?") + " — run tools/update.ps1";
      } else {
        notice.classList.add("hidden");
      }
    }
  );
}

// storage-only toggles
STORAGE_TOGGLES.forEach(function (key) {
  const el = document.getElementById(key);
  if (!el) return;
  el.addEventListener("change", function () {
    chrome.storage.local.set({ [key]: el.checked });
  });
});

// Performance mode (default OFF, so handled outside STORAGE_TOGGLES)
document.getElementById("perfMode").addEventListener("change", function (e) {
  chrome.storage.local.set({ perfMode: e.target.checked });
});

// Twitch fullscreen chat overlay (default OFF)
document.getElementById("twitchChatOverlay").addEventListener("change", function (e) {
  chrome.storage.local.set({ twitchChatOverlay: e.target.checked });
});

// Reclaim "always on" (default OFF — Reclaim is auto by default)
(function () {
  var el = document.getElementById("ytReclaimAlways");
  if (el) el.addEventListener("change", function (e) {
    chrome.storage.local.set({ ytReclaimAlways: e.target.checked });
  });
})();

// Twitch force source quality (default OFF)
document.getElementById("sysToggle").addEventListener("change", function (e) {
  chrome.storage.local.set({ sysOpen: e.target.checked }); // system.js (on the page) opens/closes the panel
});
document.getElementById("sysAuto").addEventListener("change", function (e) {
  chrome.storage.local.set({ sysAuto: e.target.checked }); // auto-summon the daily quest once a day
});
document.getElementById("twitchForceQuality").addEventListener("change", function (e) {
  chrome.storage.local.set({ twitchForceQuality: e.target.checked });
});

// EasyList toggle also flips the DNR ruleset via the background worker
document.getElementById("easylist").addEventListener("change", function (e) {
  const on = e.target.checked;
  chrome.storage.local.set({ easylistEnabled: on });
  chrome.runtime.sendMessage({ type: "setRuleset", id: "easylist", enabled: on });
});

// per-site allowlist
document.getElementById("allowToggle").addEventListener("click", function () {
  if (!currentHost) return;
  const dom = baseDomain(currentHost);
  chrome.storage.local.get("allowlist", function (data) {
    let list = data.allowlist || [];
    if (list.includes(dom)) list = list.filter(function (d) { return d !== dom; });
    else list.push(dom);
    chrome.storage.local.set({ allowlist: list }, render);
  });
});

// open the download page for the new build (we can't self-install off-store)
document.getElementById("getUpdate").addEventListener("click", function () {
  chrome.storage.local.get("selfUpdateUrl", function (d) {
    const url = d.selfUpdateUrl || "https://dl.maxxtopia.com/adblockmaxxer-chrome.zip";
    chrome.tabs.create({ url });
    window.close();
  });
});

document.getElementById("copyUpdate").addEventListener("click", function () {
  navigator.clipboard.writeText(UPDATE_CMD).then(function () {
    const b = document.getElementById("copyUpdate");
    b.textContent = "Copied!";
    setTimeout(function () { b.textContent = "Copy update command"; }, 1500);
  });
});

document.getElementById("resetCount").addEventListener("click", function (e) {
  e.preventDefault();
  chrome.storage.local.set({ adsSkipped: 0 }, render);
});

// snooze / resume
document.getElementById("snooze").addEventListener("click", function () {
  chrome.storage.local.get("snoozeUntil", function (d) {
    const snoozed = (d.snoozeUntil || 0) - Date.now() > 0;
    chrome.runtime.sendMessage({ type: snoozed ? "unsnooze" : "snooze", minutes: 5 });
    setTimeout(render, 60);
  });
});

// toggle the floating panel on the active tab (same path as the keyboard command)
document.getElementById("panel").addEventListener("click", function () {
  chrome.tabs.query({ active: true, currentWindow: true }, function (tabs) {
    const tab = tabs && tabs[0];
    const id = tab && tab.id;
    if (id == null) return;
    chrome.tabs.sendMessage(id, { type: "cmd", cmd: "toggle-panel" }, function () {
      const err = chrome.runtime.lastError;
      if (!err) { window.close(); return; }
      // Only (re)inject when the page genuinely has NO content script. Any other error
      // (e.g. "message port closed") must not trigger a second toggle — that would build
      // the panel then immediately tear it back down.
      const noReceiver = /Receiving end does not exist|Could not establish connection/i.test(err.message || "");
      const injectable = noReceiver && chrome.scripting && /^https?:/.test(tab.url || "");
      if (!injectable) { window.close(); return; }
      chrome.scripting.executeScript({ target: { tabId: id }, files: ["src/content/panel.js"] }, function () {
        if (chrome.runtime.lastError) { window.close(); return; }
        chrome.tabs.sendMessage(id, { type: "cmd", cmd: "toggle-panel" }, function () {
          if (chrome.runtime.lastError) { /* give up quietly */ }
          window.close();
        });
      });
    });
  });
});

// "Re-test now" — clear the YouTube pause on any open YouTube tab and reload it to re-attempt
// blocking. If still enforced, the content script re-sets the flag; if YouTube lifted it, we go
// ad-free again. Optimistically clear the popup flag so the UI updates immediately.
document.getElementById("ytRetest").addEventListener("click", function () {
  chrome.tabs.query({ url: ["*://*.youtube.com/*", "*://*.youtube-nocookie.com/*"] }, function (tabs) {
    (tabs || []).forEach(function (t) {
      try { chrome.tabs.sendMessage(t.id, { type: "cmd", cmd: "yt-retest" }, function () { void chrome.runtime.lastError; }); } catch (e) {}
    });
    chrome.storage.local.set({ ytEnforced: false });
    window.close();
  });
});

document.getElementById("openOptions").addEventListener("click", function (e) {
  e.preventDefault();
  if (chrome.runtime.openOptionsPage) chrome.runtime.openOptionsPage();
  else chrome.tabs.create({ url: chrome.runtime.getURL("src/options/options.html") });
});

document.getElementById("openMobile").addEventListener("click", function (e) {
  e.preventDefault();
  chrome.tabs.create({ url: chrome.runtime.getURL("src/popup/mobile.html") });
});

// figure out the active tab's host for the allowlist button
chrome.tabs.query({ active: true, currentWindow: true }, function (tabs) {
  try {
    if (tabs && tabs[0] && tabs[0].url) currentHost = new URL(tabs[0].url).hostname;
  } catch (e) {}
  render();
});

// fire a fresh update check whenever the popup opens (cheap; storage.onChanged re-renders).
// The scheduled 12h alarm is the baseline; this makes "is there an update?" feel instant.
chrome.runtime.sendMessage({ type: "checkSelfUpdate" }, function () {
  if (chrome.runtime.lastError) { /* worker asleep / no response — the alarm still covers it */ }
});

chrome.storage.onChanged.addListener(render);
