// 聊天室娱乐大厅弹窗逻辑，集中加载游戏状态并渲染入口卡片。

import { escapeHtml } from "./html.js";

const GAME_HALL_CACHE_TTL = 15000;

let gameHallEventsBound = false;
let gameHallStatusCache = null;
let gameHallStatusCacheAt = 0;

/**
 * 获取游戏大厅弹窗元素。
 *
 * @returns {HTMLElement|null}
 */
function getGameHallModal() {
    return document.getElementById("game-hall-modal");
}

/**
 * 读取服务端注入的游戏开关快照。
 *
 * @returns {Record<string, boolean>}
 */
function readGameEnabledSnapshot() {
    const modal = getGameHallModal();
    if (!modal?.dataset.gameEnabled) {
        return {};
    }

    try {
        return JSON.parse(modal.dataset.gameEnabled);
    } catch (error) {
        console.warn("[游戏大厅] 游戏开关数据解析失败:", error);
        return {};
    }
}

/**
 * 打开 Alpine 管理的游戏面板。
 *
 * @param {string} panelId
 * @param {string} [method]
 * @returns {void}
 */
function openAlpinePanel(panelId, method = "show") {
    const panel = document.getElementById(panelId);
    if (!panel || !window.Alpine) {
        return;
    }

    const data = window.Alpine.$data(panel);
    if (typeof data?.[method] === "function") {
        data[method]();
        return;
    }

    data[method] = true;
}

/**
 * 游戏大厅配置定义。
 *
 * @returns {Array<object>}
 */
function createGameDefinitions() {
    return [
        {
            id: "baccarat",
            name: "🎲 百家乐",
            desc: "猜骰子大小，1:1 赔率，豹子 1:24",
            accentColor: "#336699",
            fetchUrl: "/baccarat/current",
            openFn: () => {
                closeGameHall();
                openAlpinePanel("baccarat-panel");
            },
            renderStatus: (data) => {
                if (!data?.round) {
                    return {
                        badge: "⏸ 等待开局",
                        badgeStyle: "background:#e8f0f8; color:#336699; border:1px solid #b8d0e8",
                        detail: "下局即将开始，稍后再来",
                    };
                }

                const round = data.round;
                if (round.status === "betting") {
                    return {
                        badge: "🟢 押注中",
                        badgeStyle: "background:#d1fae5; color:#065f46; border:1px solid #6ee7b7",
                        detail: `⏱ 剩余 ${round.seconds_left || 0} 秒 | 注池：${Number((round.total_bet_big || 0) + (round.total_bet_small || 0) + (round.total_bet_triple || 0)).toLocaleString()} 金`,
                    };
                }

                return {
                    badge: "⏳ 开奖中",
                    badgeStyle: "background:#fef3c7; color:#92400e; border:1px solid #fcd34d",
                    detail: "正在摇骰子…",
                };
            },
            btnLabel: (data) => data?.round?.status === "betting" ? "🎲 立即下注" : "📊 查看详情",
        },
        {
            id: "baccarat_loss_cover",
            name: "🎁 买单活动",
            desc: "查看“你玩游戏我买单”活动，补偿领取和个人历史记录",
            accentColor: "#16a34a",
            fetchUrl: "/baccarat-loss-cover/summary",
            openFn: () => {
                closeGameHall();
                void window.openBaccaratLossCoverModal?.("overview");
            },
            renderStatus: (data) => {
                const event = data?.event;
                if (!event) {
                    return {
                        badge: "📭 暂无活动",
                        badgeStyle: "background:#e8f0f8; color:#336699; border:1px solid #b8d0e8",
                        detail: "当前没有进行中或待领取的买单活动",
                    };
                }

                const myStatus = event.my_record?.claim_status_label || "未参与";
                const total = Number(event.total_claimed_amount || 0).toLocaleString();

                if (event.status === "active") {
                    return {
                        badge: "🟢 进行中",
                        badgeStyle: "background:#d1fae5; color:#065f46; border:1px solid #6ee7b7",
                        detail: `我的状态：${myStatus} | 开启人：${event.creator_username || ""}`,
                    };
                }

                if (event.status === "settlement_pending") {
                    return {
                        badge: "⏳ 结算中",
                        badgeStyle: "background:#fef3c7; color:#92400e; border:1px solid #fcd34d",
                        detail: `活动已结束，等待最后几局结算 | 我的状态：${myStatus}`,
                    };
                }

                if (event.status === "claimable") {
                    return {
                        badge: "💰 可领取",
                        badgeStyle: "background:#dcfce7; color:#166534; border:1px solid #86efac",
                        detail: `我的状态：${myStatus} | 已发补偿 ${total} 金币`,
                    };
                }

                return {
                    badge: "🕒 即将开始",
                    badgeStyle: "background:#ede9fe; color:#5b21b6; border:1px solid #c4b5fd",
                    detail: `开启人：${event.creator_username || ""} | 我的状态：${myStatus}`,
                };
            },
            btnLabel: (data) => data?.event?.status === "claimable" ? "💰 查看并领取" : "📜 查看活动",
        },
        {
            id: "slot_machine",
            name: "🎰 老虎机",
            desc: "每日限额旋转，中奖即时到账",
            accentColor: "#0891b2",
            fetchUrl: null,
            openFn: () => {
                closeGameHall();
                openAlpinePanel("slot-panel");
            },
            renderStatus: () => ({
                badge: "✅ 随时可玩",
                badgeStyle: "background:#d1fae5; color:#065f46; border:1px solid #6ee7b7",
                detail: "每日限额抽奖，旋转即可",
            }),
            btnLabel: () => "🎰 开始旋转",
        },
        {
            id: "mystery_box",
            name: "📦 神秘箱子",
            desc: "管理员随机投放，抢到即开奖",
            accentColor: "#b45309",
            fetchUrl: "/mystery-box/status",
            openFn: () => {
                closeGameHall();
                window.dispatchEvent(new CustomEvent("open-mystery-box"));
            },
            renderStatus: (data) => {
                const count = data?.available_count ?? 0;

                return count > 0 ? {
                    badge: `🎁 ${count} 个待领`,
                    badgeStyle: "background:#fef3c7; color:#92400e; border:1px solid #fcd34d",
                    detail: "箱子已投放！快去领取",
                } : {
                    badge: "📭 暂无箱子",
                    badgeStyle: "background:#e8f0f8; color:#336699; border:1px solid #b8d0e8",
                    detail: "等待管理员投放",
                };
            },
            btnLabel: (data) => (data?.available_count ?? 0) > 0 ? "🎁 立即领取" : "📭 等待投放",
        },
        {
            id: "horse_racing",
            name: "🐎 赛马竞猜",
            desc: "彩池制赛马，押注马匹赢取奖金",
            accentColor: "#336699",
            fetchUrl: "/horse-race/current",
            openFn: () => {
                closeGameHall();
                openAlpinePanel("horse-race-panel", "openFromHall");
            },
            renderStatus: (data) => {
                if (!data?.race) {
                    return {
                        badge: "⏸ 等待开赛",
                        badgeStyle: "background:#e8f0f8; color:#336699; border:1px solid #b8d0e8",
                        detail: "下场赛马即将开始",
                    };
                }

                const race = data.race;
                if (race.status === "betting") {
                    return {
                        badge: "🟢 押注中",
                        badgeStyle: "background:#d1fae5; color:#065f46; border:1px solid #6ee7b7",
                        detail: `⏱ 剩余 ${race.seconds_left || 0} 秒 | 注池：${Number(race.total_pool || 0).toLocaleString()} 金`,
                    };
                }

                if (race.status === "running") {
                    return {
                        badge: "🏇 跑马中",
                        badgeStyle: "background:#fef3c7; color:#92400e; border:1px solid #fcd34d",
                        detail: "比赛进行中…",
                    };
                }

                return {
                    badge: "🏆 已结算",
                    badgeStyle: "background:#e8f0f8; color:#336699; border:1px solid #b8d0e8",
                    detail: "下场即将开始",
                };
            },
            btnLabel: (data) => data?.race?.status === "betting" ? "🐎 立即押注" : "📊 查看赛况",
        },
        {
            id: "fortune_telling",
            name: "🔮 神秘占卜",
            desc: "每日签文，开启今日运势加成",
            accentColor: "#6d28d9",
            fetchUrl: "/fortune/today",
            openFn: () => {
                closeGameHall();
                openAlpinePanel("fortune-panel");
            },
            renderStatus: (data) => {
                if (!data?.enabled) {
                    return {
                        badge: "🔒 未开启",
                        badgeStyle: "background:#e8f0f8; color:#336699; border:1px solid #b8d0e8",
                        detail: "此游戏暂未开启",
                    };
                }

                const used = data.free_used ?? 0;
                const total = data.free_count ?? 1;

                return data.has_free_left ? {
                    badge: "✨ 免费可占",
                    badgeStyle: "background:#ede9fe; color:#5b21b6; border:1px solid #c4b5fd",
                    detail: `今日已占 ${used}/${total} 次，还有免费次数`,
                } : {
                    badge: "💰 付费可占",
                    badgeStyle: "background:#e8f0f8; color:#336699; border:1px solid #b8d0e8",
                    detail: `今日免费次数已用完（${data.extra_cost} 金/次）`,
                };
            },
            btnLabel: (data) => data?.has_free_left ? "🔮 免费占卜" : "🔮 付费占卜",
        },
        {
            id: "fishing",
            name: "🎣 钓鱼",
            desc: "消耗鱼饵钓取金币和道具。背包需有鱼饵才能出竿。",
            accentColor: "#0d9488",
            fetchUrl: null,
            openFn: () => {
                closeGameHall();
                window.startFishing?.();
            },
            renderStatus: () => ({
                badge: "🎣 随时可钓",
                badgeStyle: "background:#d1fae5; color:#065f46; border:1px solid #6ee7b7",
                detail: "① 点击发言框上方【🎣 钓鱼】按钮 → ② 等待浮漂出现 → ③ 看到 🪝 后立刻点击收竿！",
            }),
            btnLabel: () => "🎣 去钓鱼",
        },
        {
            id: "lottery",
            name: "🎟️ 双色球",
            desc: "每日20:00开奖，选3红1蓝，按奖池比例派奖，无一等奖滚存累积",
            accentColor: "#dc2626",
            fetchUrl: "/lottery/current",
            openFn: () => {
                closeGameHall();
                window.openLotteryPanel?.();
            },
            renderStatus: (data) => {
                if (!data?.issue) {
                    return {
                        badge: "⏸ 等待开期",
                        badgeStyle: "background:#e8f0f8; color:#336699; border:1px solid #b8d0e8",
                        detail: "暂无进行中期次",
                    };
                }

                const issue = data.issue;
                const pool = Number(issue.pool_amount || 0).toLocaleString();
                if (data.is_open) {
                    const hours = Math.floor(issue.seconds_left / 3600);
                    const minutes = Math.floor((issue.seconds_left % 3600) / 60);
                    const timeText = hours > 0 ? `${hours}h ${minutes}m` : `${minutes}m`;

                    return {
                        badge: issue.is_super_issue ? "🎊 超级期购票中" : "🟢 购票中",
                        badgeStyle: "background:#fef2f2; color:#b91c1c; border:1px solid #fca5a5",
                        detail: `💰 奖池 ${pool} 金 | 距开奖 ${timeText} | 第 ${issue.issue_no} 期`,
                    };
                }

                if (issue.status === "settled") {
                    return {
                        badge: "✅ 已开奖",
                        badgeStyle: "background:#d1fae5; color:#065f46; border:1px solid #6ee7b7",
                        detail: "本期已开奖，下期购票中",
                    };
                }

                return {
                    badge: "🔴 已停售",
                    badgeStyle: "background:#fee2e2; color:#b91c1c; border:1px solid #fecaca",
                    detail: `💰 奖池 ${pool} 金 | 等待开奖中…`,
                };
            },
            btnLabel: (data) => data?.is_open ? "🎟️ 立即购票" : "📊 查看结果",
        },
        {
            id: "gomoku",
            name: "♟️ 五子棋",
            desc: "益智对弈，支持 PvP 随机对战和 AI 人机对战（4档难度）",
            accentColor: "#1e3a5f",
            fetchUrl: null,
            openFn: () => {
                closeGameHall();
                window.openGomokuPanel?.();
            },
            renderStatus: () => ({
                badge: "♟️ 随时对弈",
                badgeStyle: "background:#e8eef8; color:#1e3a5f; border:1px solid #9db3d4",
                detail: "PvP 胜利 +80 金币 | AI 专家难度胜利 +300 金币",
            }),
            btnLabel: () => "♟️ 开始对弈",
        },
    ];
}

/**
 * 加载游戏大厅状态，短时间内复用结果以减少重复请求。
 *
 * @returns {Promise<{enabledGames:Array<object>, statuses:Record<string, unknown>}>}
 */
async function loadGameHallStatus() {
    const now = Date.now();
    if (gameHallStatusCache && now - gameHallStatusCacheAt < GAME_HALL_CACHE_TTL) {
        return gameHallStatusCache;
    }

    const modal = getGameHallModal();
    let enabledMap = readGameEnabledSnapshot();

    try {
        const response = await fetch(modal?.dataset.gameEnabledUrl || "/games/enabled", {
            headers: {
                Accept: "application/json",
            },
        });
        if (response.ok) {
            enabledMap = await response.json();
        }
    } catch (error) {
        // 网络异常时降级使用页面注入的开关快照。
    }

    const enabledGames = createGameDefinitions().filter((game) => enabledMap[game.id] !== false);
    const statuses = {};

    await Promise.all(enabledGames.filter((game) => game.fetchUrl).map(async (game) => {
        try {
            const response = await fetch(game.fetchUrl);
            statuses[game.id] = await response.json();
        } catch (error) {
            statuses[game.id] = null;
        }
    }));

    gameHallStatusCache = { enabledGames, statuses };
    gameHallStatusCacheAt = Date.now();

    return gameHallStatusCache;
}

/**
 * 关闭游戏大厅弹窗。
 *
 * @returns {void}
 */
export function closeGameHall() {
    const modal = getGameHallModal();
    if (modal) {
        modal.style.display = "none";
    }
}

/**
 * 渲染所有游戏卡片。
 *
 * @param {Array<object>} games
 * @param {Record<string, unknown>} statuses
 * @returns {void}
 */
function renderGameCards(games, statuses) {
    const container = document.getElementById("game-hall-cards");
    const loading = document.getElementById("game-hall-loading");
    const empty = document.getElementById("game-hall-empty");
    if (!container || !loading || !empty) {
        return;
    }

    container.innerHTML = "";

    if (games.length === 0) {
        loading.style.display = "none";
        empty.style.display = "block";
        return;
    }

    games.forEach((game) => {
        try {
            const data = statuses[game.id] ?? null;
            const status = game.renderStatus ? game.renderStatus(data) : {
                badge: "✅ 可用",
                badgeStyle: "background:#d1fae5; color:#065f46; border:1px solid #6ee7b7",
                detail: "",
            };
            const buttonLabel = game.btnLabel ? game.btnLabel(data) : "🎮 进入";

            const card = document.createElement("div");
            card.style.cssText = `
                background:#fff;
                border:1px solid #d0e4f5;
                border-left:4px solid ${game.accentColor};
                border-radius:6px; padding:12px 14px;
                cursor:default; transition:border-color .2s, box-shadow .2s;
                display:flex; flex-direction:column; gap:8px;
            `;

            card.innerHTML = `
                <div style="display:flex; align-items:flex-start; justify-content:space-between; gap:8px;">
                    <div style="flex:1;">
                        <div style="color:#225588; font-weight:bold; font-size:13px; margin-bottom:3px;">${escapeHtml(game.name)}</div>
                        <div style="color:#666; font-size:11px; line-height:1.4;">${escapeHtml(game.desc)}</div>
                    </div>
                    <span style="padding:2px 8px; border-radius:10px; font-size:10px; font-weight:bold; white-space:nowrap; ${status.badgeStyle}">
                        ${escapeHtml(status.badge)}
                    </span>
                </div>
                <div style="color:#888; font-size:10px; line-height:1.4; min-height:14px; border-top:1px dashed #e0ecf8; padding-top:6px;">${status.detail ? escapeHtml(status.detail) : "&nbsp;"}</div>
                <button type="button"
                    style="width:100%; border:none; border-radius:4px; padding:7px 8px; font-size:12px; font-weight:bold;
                           cursor:pointer; color:#fff; transition:opacity .15s;
                           background:linear-gradient(135deg,${game.accentColor},${game.accentColor}cc);">
                    ${escapeHtml(buttonLabel)}
                </button>
            `;

            card.querySelector("button")?.addEventListener("click", (event) => {
                event.stopPropagation();
                game.openFn();
            });

            card.addEventListener("mouseenter", () => {
                card.style.borderColor = game.accentColor;
                card.style.boxShadow = "0 2px 8px rgba(51,102,153,.18)";
            });
            card.addEventListener("mouseleave", () => {
                card.style.borderColor = "#d0e4f5";
                card.style.borderLeftColor = game.accentColor;
                card.style.boxShadow = "";
            });

            container.appendChild(card);
        } catch (error) {
            console.warn(`[游戏大厅] 游戏 ${game.id} 卡片渲染失败:`, error);
        }
    });

    loading.style.display = "none";
    container.style.display = "grid";
}

/**
 * 打开游戏大厅弹窗并加载各游戏状态。
 *
 * @returns {Promise<void>}
 */
export async function openGameHall() {
    const modal = getGameHallModal();
    if (!modal) {
        console.error("[游戏大厅] game-hall-modal 元素不存在，请检查模板加载");
        return;
    }

    modal.style.display = "flex";

    const loading = document.getElementById("game-hall-loading");
    const cards = document.getElementById("game-hall-cards");
    const empty = document.getElementById("game-hall-empty");
    if (loading) {
        loading.style.display = "block";
    }
    if (cards) {
        cards.style.display = "none";
    }
    if (empty) {
        empty.style.display = "none";
    }

    const jjb = document.getElementById("game-hall-jjb");
    if (jjb && window.chatContext?.userJjb !== undefined) {
        jjb.textContent = Number(window.chatContext.userJjb).toLocaleString();
    }

    const { enabledGames, statuses } = await loadGameHallStatus();

    try {
        renderGameCards(enabledGames, statuses);
    } catch (error) {
        console.error("[游戏大厅] 渲染游戏卡片失败:", error);
        if (loading) {
            loading.style.display = "none";
        }
        if (empty) {
            empty.style.display = "block";
        }
    }
}

/**
 * 绑定娱乐大厅基础控件事件。
 *
 * @returns {void}
 */
export function bindGameHallControls() {
    if (gameHallEventsBound || typeof document === "undefined") {
        return;
    }

    gameHallEventsBound = true;
    window.openGameHall = openGameHall;
    window.closeGameHall = closeGameHall;

    document.addEventListener("click", (event) => {
        if (!(event.target instanceof Element)) {
            return;
        }

        if (event.target.closest("[data-game-hall-close]")) {
            event.preventDefault();
            closeGameHall();
            return;
        }

        const modal = event.target.closest("#game-hall-modal");
        if (modal && event.target === modal) {
            closeGameHall();
        }
    });
}
