/* ============================================================
   CONFIG — XP VALUES & SECTION MAPPING
   ============================================================ */

const TASK_XP = {
  // Morning
  omeprazole: 5,
  setrona_morning: 5,
  acv_morning: 5,
  greens: 5,
  mushroom: 5,
  joint: 5,
  protein_morning: 5,
  water_morning: 10,
  no_doomscroll: 10,
  light_movement: 10,

  // Midday
  l_theanine: 5,
  breathing_break: 10,
  stress_check: 5,
  coffee_here: 5,
  setrona_midday: 5,
  acv_midday: 5,
  voltaren_midday: 5,
  manshake: 5,
  midday_walk: 10,
  protein_lunch: 10,
  step_check: 10,

  // Pre-workout
  creatine: 5,
  pre_stim: 5,
  water_pre: 10,
  warmup: 10,
  energy_rating: 5,

  // Workout
  bcaa: 5,
  complete_workout: 10,
  track_reps: 5,
  stretch_post: 5,

  // Evening
  voltaren_evening: 5,
  magnesium: 5,
  inositol: 5,
  prazosin: 5,
  no_screens: 10,
  evening_breathing: 10,
  plan_meals: 10,
  sleep_goal: 10,

  // Fat-loss
  protein_target: 10,
  calorie_target: 10,
  steps_target: 10,
  water_total: 10,

  // Anxiety
  no_caffeine_after_2: 10,
  breathing_total: 10,
  sleep_routine: 10,
};

const TASK_SECTION = {
  // Morning
  omeprazole: "morning",
  setrona_morning: "morning",
  acv_morning: "morning",
  greens: "morning",
  mushroom: "morning",
  joint: "morning",
  protein_morning: "morning",
  water_morning: "morning",
  no_doomscroll: "morning",
  light_movement: "morning",

  // Midday
  l_theanine: "midday",
  breathing_break: "midday",
  stress_check: "midday",
  coffee_here: "midday",
  setrona_midday: "midday",
  acv_midday: "midday",
  voltaren_midday: "midday",
  manshake: "midday",
  midday_walk: "midday",
  protein_lunch: "midday",
  step_check: "midday",

  // Pre-workout
  creatine: "pre",
  pre_stim: "pre",
  water_pre: "pre",
  warmup: "pre",
  energy_rating: "pre",

  // Workout
  bcaa: "workout",
  complete_workout: "workout",
  track_reps: "workout",
  stretch_post: "workout",

  // Evening
  voltaren_evening: "evening",
  magnesium: "evening",
  inositol: "evening",
  prazosin: "evening",
  no_screens: "evening",
  evening_breathing: "evening",
  plan_meals: "evening",
  sleep_goal: "evening",

  // Fat-loss
  protein_target: "fat",
  calorie_target: "fat",
  steps_target: "fat",
  water_total: "fat",

  // Anxiety
  no_caffeine_after_2: "anx",
  breathing_total: "anx",
  sleep_routine: "anx",
};

const DAILY_PERFECT_BONUS = 50;
const STORAGE_KEY = "iron_dungeon_paladin_state_v1";

/* ============================================================
   STATE
   ============================================================ */

let xpTotal = 0;
let level = 1;
let streak = 0;
let todayXP = 0;
let dailyPerfect = false;
let completedTasks = {};
let days = {}; // rolling 7-day ledger

/* ============================================================
   HELPERS
   ============================================================ */

const todayISO = () => new Date().toISOString().slice(0, 10);

function formatDateShort(dateStr) {
  const d = new Date(dateStr + "T00:00:00");
  return d.toLocaleDateString(undefined, {
    weekday: "short",
    month: "short",
    day: "numeric",
  });
}

function getXPToNextLevel(level) {
  if (level <= 1) return 500;
  if (level <= 2) return 1000;
  if (level <= 3) return 1500;
  if (level <= 4) return 2000;
  if (level <= 10) return 2500;
  if (level <= 20) return 3000;
  if (level <= 30) return 4000;
  if (level <= 40) return 5000;
  return 7500;
}

function updateLevel() {
  let xpNeeded = getXPToNextLevel(level);
  while (xpTotal >= xpNeeded && level < 50) {
    xpTotal -= xpNeeded;
    level++;
    xpNeeded = getXPToNextLevel(level);
    animateLevelUp();
  }
}

/* ============================================================
   UI UPDATES
   ============================================================ */

function updateUI() {
  document.getElementById("level").textContent = level;
  document.getElementById("xp").textContent = xpTotal;
  document.getElementById("streak").textContent = streak;

  const xpToNext = getXPToNextLevel(level);
  document.getElementById("xp-to-next").textContent = xpToNext;

  const ratio = Math.min(1, xpTotal / xpToNext);
  document.getElementById("xp-bar").style.width = `${ratio * 100}%`;

  // restore checkbox states
  document.querySelectorAll("input[type=checkbox][data-task-id]").forEach(cb => {
    cb.checked = !!completedTasks[cb.dataset.taskId];
  });

  renderWeeklyView();
}

function animateXP() {
  const bar = document.getElementById("xp-bar");
  bar.classList.add("xp-animate");
  setTimeout(() => bar.classList.remove("xp-animate"), 300);
}

function animateLevelUp() {
  const header = document.querySelector(".header-panel");
  header.classList.add("levelup-glow");
  setTimeout(() => header.classList.remove("levelup-glow"), 800);
}

/* ============================================================
   XP LOGIC
   ============================================================ */

function addXP(amount) {
  xpTotal += amount;
  todayXP += amount;
  animateXP();
  updateLevel();
  updateUI();
  saveState();
}

/* ============================================================
   SAVE / LOAD
   ============================================================ */

function saveState() {
  const state = {
    xpTotal,
    level,
    streak,
    todayXP,
    dailyPerfect,
    completedTasks,
    days,
    lastDate: todayISO(),
  };
  localStorage.setItem(STORAGE_KEY, JSON.stringify(state));
}

function loadState() {
  const raw = localStorage.getItem(STORAGE_KEY);
  if (!raw) return;

  try {
    const state = JSON.parse(raw);
    const today = todayISO();

    days = state.days || {};

    if (state.lastDate !== today) {
      xpTotal = state.xpTotal || 0;
      level = state.level || 1;
      streak = state.streak || 0;
      todayXP = 0;
      dailyPerfect = false;
      completedTasks = {};
    } else {
      xpTotal = state.xpTotal || 0;
      level = state.level || 1;
      streak = state.streak || 0;
      todayXP = state.todayXP || 0;
      dailyPerfect = state.dailyPerfect || false;
      completedTasks = state.completedTasks || {};
    }
  } catch (e) {
    console.error("Failed to load state", e);
  }
}

/* ============================================================
   TASK HANDLING
   ============================================================ */

function onTaskToggle(e) {
  const cb = e.target;
  if (cb.tagName !== "INPUT" || cb.type !== "checkbox") return;

  const id = cb.dataset.taskId;
  const xp = TASK_XP[id] || 0;

  if (cb.checked) {
    completedTasks[id] = true;
    addXP(xp);
  } else {
    delete completedTasks[id];
    xpTotal -= xp;
    todayXP -= xp;
    if (xpTotal < 0) xpTotal = 0;
    if (todayXP < 0) todayXP = 0;
    updateLevel();
    updateUI();
    saveState();
  }
}

/* ============================================================
   DAILY PERFECT
   ============================================================ */

function markDailyPerfect() {
  if (dailyPerfect) return;
  dailyPerfect = true;
  streak++;
  addXP(DAILY_PERFECT_BONUS);
}

/* ============================================================
   SAVE DAY (ROLLING LEDGER)
   ============================================================ */

function computeSections(taskMap) {
  const sections = {
    morning: 0,
    midday: 0,
    pre: 0,
    workout: 0,
    evening: 0,
    fat: 0,
    anx: 0,
  };

  let total = 0;

  for (const id of Object.keys(taskMap)) {
    const xp = TASK_XP[id] || 0;
    const sec = TASK_SECTION[id] || "morning";
    sections[sec] += xp;
    total += xp;
  }

  if (dailyPerfect) total += DAILY_PERFECT_BONUS;

  return { total, sections };
}

function saveDay() {
  const date = todayISO();
  const { total, sections } = computeSections(completedTasks);

  days[date] = {
    totalXP: total,
    sections,
    dailyPerfect,
  };

  saveState();
  alert("Day saved.");
}

/* ============================================================
   EXPORT / IMPORT
   ============================================================ */

function exportJSON() {
  const raw = localStorage.getItem(STORAGE_KEY) || "{}";
  const blob = new Blob([raw], { type: "application/json" });
  const url = URL.createObjectURL(blob);

  const a = document.createElement("a");
  a.href = url;
  a.download = "iron_dungeon_save.json";
  document.body.appendChild(a);
  a.click();
  a.remove();

  URL.revokeObjectURL(url);
}

function importJSON(file) {
  const reader = new FileReader();
  reader.onload = e => {
    try {
      localStorage.setItem(STORAGE_KEY, e.target.result);
      loadState();
      updateUI();
      alert("Save imported.");
    } catch {
      alert("Import failed.");
    }
  };
  reader.readAsText(file);
}

/* ============================================================
   WEEKLY LEDGER
   ============================================================ */

function getLast7Dates() {
  const arr = [];
  const today = new Date(todayISO() + "T00:00:00");

  for (let i = 6; i >= 0; i--) {
    const d = new Date(today);
    d.setDate(d.getDate() - i);
    arr.push(d.toISOString().slice(0, 10));
  }
  return arr;
}

function renderWeeklyView() {
  const tbody = document.getElementById("weekly-table-body");
  const bars = document.getElementById("weekly-bars");
  const summary = document.getElementById("weekly-summary");

  tbody.innerHTML = "";
  bars.innerHTML = "";
  summary.textContent = "";

  const dates = getLast7Dates();
  let maxXP = 0;
  let weeklyTotal = 0;
  let perfectCount = 0;

  const rows = dates.map(date => {
    const entry = days[date] || {
      totalXP: 0,
      sections: {
        morning: 0,
        midday: 0,
        pre: 0,
        workout: 0,
        evening: 0,
        fat: 0,
        anx: 0,
      },
      dailyPerfect: false,
    };

    if (entry.totalXP > maxXP) maxXP = entry.totalXP;
    weeklyTotal += entry.totalXP;
    if (entry.dailyPerfect) perfectCount++;

    return { date, entry };
  });

  // Table rows
  rows.forEach(({ date, entry }) => {
    const tr = document.createElement("tr");

    tr.innerHTML = `
      <td>${formatDateShort(date)}</td>
      <td>${entry.totalXP}</td>
      <td>${entry.sections.morning}</td>
      <td>${entry.sections.midday}</td>
      <td>${entry.sections.pre}</td>
      <td>${entry.sections.workout}</td>
      <td>${entry.sections.evening}</td>
      <td>${entry.sections.fat}</td>
      <td>${entry.sections.anx}</td>
      <td>${entry.dailyPerfect ? "⭐" : ""}</td>
    `;

    tbody.appendChild(tr);
  });

  // Bars
  rows.forEach(({ date, entry }) => {
    const bar = document.createElement("div");
    bar.className = "ledger-bar";

    const fill = document.createElement("div");
    fill.className = "ledger-bar-fill";
    fill.style.height = maxXP ? `${(entry.totalXP / maxXP) * 100}%` : "0%";

    const label = document.createElement("div");
    label.className = "ledger-bar-label";
    label.textContent = new Date(date).toLocaleDateString(undefined, {
      weekday: "short",
    });

    bar.appendChild(fill);
    bar.appendChild(label);
    bars.appendChild(bar);
  });

  summary.textContent = `Weekly total: ${weeklyTotal} XP • Perfect days: ${perfectCount}/7`;
}

/* ============================================================
   PRODUCTS.TXT PARSER
   ============================================================ */

async function loadProducts() {
  try {
    const res = await fetch("https://idontbyte.com/products/products.txt");
    const text = await res.text();
    const products = parseProducts(text);
    renderProducts(products);
  } catch (e) {
    console.error("Failed to load products:", e);
  }
}

function parseProducts(text) {
  const blocks = text
    .split(/\n\s*\n/)
    .map(b => b.trim())
    .filter(Boolean);

  return blocks.map(block => {
    const lines = block.split("\n").map(l => l.trim()).filter(Boolean);

    return {
      name: lines[0] || "",
      category: lines[1] || "",
      status: lines[2] || "",
      imageUrl: lines[3] || "",
      subtitle: lines[4]?.replace(/^Subtitle:\s*/i, "") || "",
      link: lines[5] || "",
    };
  });
}

function renderProducts(products) {
  const container = document.getElementById("products-container");
  container.innerHTML = "";

  products.forEach(p => {
    const card = document.createElement("div");
    card.className = "loot-card";

    card.innerHTML = `
      <img src="${p.imageUrl}" alt="${p.name}" />
      <div class="loot-info">
        <div class="loot-name">${p.name}</div>
        <div class="loot-meta">${p.category} • ${p.status}</div>
        <div class="loot-meta">${p.subtitle}</div>
        <a href="${p.link}" target="_blank" class="loot-link">View</a>
      </div>
    `;

    container.appendChild(card);
  });
}

/* ============================================================
   INIT
   ============================================================ */

function init() {
  loadState();
  updateUI();

  document.querySelectorAll(".quest-list").forEach(list => {
    list.addEventListener("change", onTaskToggle);
  });

  document.getElementById("daily-perfect-btn").addEventListener("click", markDailyPerfect);
  document.getElementById("save-day-btn").addEventListener("click", saveDay);

  document.getElementById("export-btn").addEventListener("click", exportJSON);
  document.getElementById("import-input").addEventListener("change", e => {
    if (e.target.files[0]) importJSON(e.target.files[0]);
  });

  const toggle = document.getElementById("weekly-toggle");
  const body = document.getElementById("weekly-body");
  const arrow = document.getElementById("weekly-arrow");

  toggle.addEventListener("click", () => {
    const open = body.classList.toggle("open");
    arrow.textContent = open ? "▲" : "▼";
  });

  loadProducts();
}

document.addEventListener("DOMContentLoaded", init);