const ws = new WebSocket(`/api/status`);

document.addEventListener("DOMContentLoaded", () => {
    ws.addEventListener("open", () => {
        ws.send(JSON.stringify({ type: "getStatus" }));
        ws.send(JSON.stringify({ type: "getUsers" }));
    });
    
    ws.addEventListener("message", (event) => {
        handleMessage(event);
    });
    
    ws.addEventListener("close", () => {
        // console.log("WebSocket connection closed.");
    });
    
    ws.addEventListener("error", (error) => {
        console.error("WebSocket error:", error);
    });

    const bannerElem = document.getElementById("banner");
    const avatar_custom_container = document.getElementById("avatar-custom-container",);
    const avatarElem = document.getElementById("avatar");
    const displayNameElem = document.getElementById("display-name");
    const decorationElem = document.getElementById("avatar-decoration");
    const usernameElem = document.getElementById("username");
    const statusCircle = document.getElementById("status-circle");
    const badgeContainer = document.getElementById("badge-container");

    const about_me_tab = document.getElementById("about-me-content");
    const about_me_tab_button = document.getElementById("about-me");
    const activity_tab = document.getElementById("activity-content");
    const activity_tab_button = document.getElementById("activity");

    // const placeholderAvatar = "/public/images/avatar-placeholder.png";
    const placeholderUsername = "Loading...";

    // avatarElem.src = placeholderAvatar;
    usernameElem.textContent = placeholderUsername;
    decorationElem.style.display = "none";

    function handleMessage(event) {
        const data = JSON.parse(event.data);

        if (data.type === "statusUpdate") {
            handleStatusUpdate(data.status);
        } else if (data.type === "presenceUpdate") {
            handlePresenceUpdate(data.presence);
        } else if (data.type === "usersUpdate") {
            handleUsersUpdate(data.users);
        } else if (data.type === "badgesUpdate") {
            handleBadges(data.badges);
        }
    }

    function updateStatusCircle(status) {
        if (!statusCircle || !status) return;

        statusCircle.classList.remove("online", "idle", "dnd", "offline");
        statusCircle.classList.add(status);
    }

    function typeText(type) {
        switch (type) {
            case 0:
                return "Playing";
            case 1:
                return "Streaming";
            case 2:
                return "Listening to";
            case 3:
                return "Watching";
            case 4:
                return "Custom Status";
            default:
                return "Unknown";
        }
    }

    const tabButtons = document.querySelectorAll(".tab-button");

    tabButtons.forEach((button) => {
        const type = button.getAttribute("data-type");

        button.addEventListener("click", () => {
            tabSwitch(type);
        });
    });

    function tabSwitch(tab) {
        if (tab === "activity") {
            about_me_tab.classList.remove("active");
            about_me_tab_button.classList.remove("active");
            about_me_tab.classList.add("hidden");

            activity_tab.classList.add("active");
            activity_tab_button.classList.add("active");
            activity_tab.classList.remove("hidden");
        } else {
            activity_tab.classList.remove("active");
            activity_tab_button.classList.remove("active");
            activity_tab.classList.add("hidden");

            about_me_tab.classList.add("active");
            about_me_tab_button.classList.add("active");
            about_me_tab.classList.remove("hidden");
        }
    }

    function updateActivities(activities) {
        const activityList = document.createElement("div");
        const customStatusText = document.getElementById("custom-status-text");
        activityList.id = "activity-list";

        const shouldShowNoActivity = activities.length === 0 || (activities.length === 1 && activities[0]?.type === 4);
        if (shouldShowNoActivity) {
            const noActivity = document.createElement("p");
            noActivity.classList.add("no-activity");
            noActivity.textContent = "No activity(s) to display";
            activityList.appendChild(noActivity);

            tabSwitch("about-me");
        }

        const existingActivities = document.getElementById("activity-list");

        if (existingActivities) existingActivities.remove();
        if (customStatusText) customStatusText.remove();

        activities.forEach((activity) => {
            if (activity.type === 4) {
                const customStatusDiv = document.createElement("div");
                customStatusDiv.classList.add("custom-status");

                const customStatus = document.createElement("p");
                customStatus.classList.add("custom-status-text");
                customStatus.id = "custom-status-text";
                customStatus.textContent = activity.state;

                customStatusDiv.appendChild(customStatus);
                avatar_custom_container.appendChild(customStatusDiv);

                return;
            }

            const activityDiv = document.createElement("div");
            activityDiv.classList.add("activity");

            let activityLargeText;

            const activityTypeDiv = document.createElement("div");
            activityTypeDiv.classList.add("activity-type-container");

            const activityType = document.createElement("p");
            activityType.classList.add("activity-type");

            if (activity.type === 2) {
                activityType.textContent = `${typeText(activity.type)} ${activity.name}`;
            } else {
                activityType.textContent = `${typeText(activity.type)}`;
            }

            activityTypeDiv.appendChild(activityType);
            activityDiv.appendChild(activityTypeDiv);

            const activityContentDiv = document.createElement("div");
            activityContentDiv.classList.add("activity-content");

            if (activity.assets?.largeImage) {
                const largeImageDiv = document.createElement("div");
                largeImageDiv.classList.add("large-image");

                if (activity.assets.largeText && activity.type === 2)
                    activityLargeText = activity.assets.largeText;

                const largeImage = document.createElement("img");
                largeImage.src = parseDiscordImage(
                    activity.assets.largeImage,
                    activity.applicationID,
                );
                largeImage.alt = "Large Image";
                largeImage.classList.add("asset-large-image");
                largeImageDiv.appendChild(largeImage);

                if (activity.assets?.smallImage) {
                    const smallImageDiv = document.createElement("div");
                    smallImageDiv.classList.add("small-image");

                    const smallImage = document.createElement("img");
                    smallImage.src = parseDiscordImage(
                        activity.assets.smallImage,
                        activity.applicationID,
                    );
                    smallImage.alt = "Small Image";
                    smallImage.classList.add("asset-small-image");
                    smallImageDiv.appendChild(smallImage);

                    largeImageDiv.appendChild(smallImageDiv);
                }

                activityContentDiv.appendChild(largeImageDiv);
            }

            const activityInfoDiv = document.createElement("div");
            activityInfoDiv.classList.add("activity-info");

            const name = document.createElement("p");
            name.classList.add("activity-name");
            if (activity.type === 2) {
                name.textContent = `${activity.details}`;
            } else {
                name.textContent = `${activity.name}`;
            }
            activityInfoDiv.appendChild(name);

            if (activity.details && activity.type !== 2) {
                const details = document.createElement("p");
                details.classList.add("activity-details");
                details.textContent = `${activity.details}`;
                activityInfoDiv.appendChild(details);
            }

            if (activity.state) {
                const state = document.createElement("p");
                state.classList.add("activity-state");
                state.textContent = `${activity.state}`;
                activityInfoDiv.appendChild(state);
            }

            if (activityLargeText) {
                const largeText = document.createElement("p");
                largeText.classList.add("activity-large-text");
                largeText.textContent = `${activityLargeText}`;
                activityInfoDiv.appendChild(largeText);
            }

            if (activity.timestamps?.start) {
                const timestamp = document.createElement("p");
                timestamp.classList.add("activity-timestamp");
                const startTime = activity.timestamps.start;

                function updateElapsedTime() {
                    const elapsedTime = getElapsedTime(startTime);
                    timestamp.innerHTML = `<img src="/public/assets/game_icon.svg" alt="Time icon"> ${elapsedTime}`;
                }

                updateElapsedTime();

                setInterval(updateElapsedTime, 1000);

                activityInfoDiv.appendChild(timestamp);
            }

            activityContentDiv.appendChild(activityInfoDiv);
            activityDiv.appendChild(activityContentDiv);

            activityList.appendChild(activityDiv);
        });

        activity_tab.appendChild(activityList);
    }

    function getElapsedTime(startTimestamp) {
        const now = Date.now();
        const elapsed = now - startTimestamp;

        const seconds = Math.floor(elapsed / 1000) % 60;
        const minutes = Math.floor(elapsed / (1000 * 60)) % 60;
        const hours = Math.floor(elapsed / (1000 * 60 * 60)) % 24;
        const days = Math.floor(elapsed / (1000 * 60 * 60 * 24));

        let formattedTime = "";

        if (days > 0) {
            formattedTime += `${days}:`;
        }
        if (hours > 0 || days > 0) {
            formattedTime += `${pad(hours)}:`;
        }
        if (minutes > 0 || hours > 0 || days > 0) {
            formattedTime += `${pad(minutes)}:`;
        }

        formattedTime += `${pad(seconds)}`;

        return formattedTime;
    }

    function pad(value) {
        return String(value).padStart(2, "0");
    }

    function handleStatusUpdate(status) {
        const firstUser = Object.values(status)[0];
        const userStatus = firstUser?.status;
        const activities = firstUser?.activities || [];

        updateStatusCircle(userStatus);
        updateActivities(activities);
    }

    function handlePresenceUpdate(presence) {
        const userPresence = presence?.status;
        const activities = presence?.activities || [];

        updateStatusCircle(userPresence);
        updateActivities(activities);
    }

    function parseDiscordImage(imageUrl, activityID) {
        if (imageUrl.startsWith("mp:external/")) {
            const httpsIndex = imageUrl.indexOf("https/");
            if (httpsIndex !== -1) {
                return "https://" + imageUrl.slice(httpsIndex + "https/".length);
            }
        } else if (/^\d+$/.test(imageUrl)) {
            return `https://cdn.discordapp.com/app-assets/${activityID}/${imageUrl}`;
        }
        return imageUrl;
    }

    function handleUsersUpdate(users) {
        const firstUser = Object.values(users)[0];

        ws.send(JSON.stringify({ type: "getBadges", userId: firstUser.id }));
        if (!firstUser || !firstUser.user) return;

        const { avatar, avatarDecoration, username, banner } = firstUser;
        const displayName = firstUser.user.globalName || firstUser.user.username;

        updateUserInfo(avatar, avatarDecoration, username, displayName, banner);
    }

    function updateUserInfo(
        avatarUrl,
        decorationUrl,
        username,
        displayName,
        banner,
    ) {
        if (bannerElem) {
            bannerElem.src = banner + "?size=2048" || "";
        }

        if (avatarElem) {
            avatarElem.src = avatarUrl; //|| placeholderAvatar;
        }

        if (decorationElem) {
            if (decorationUrl) {
                decorationElem.src = decorationUrl;
                decorationElem.style.display = "block";
            } else {
                decorationElem.style.display = "none";
            }
        }

        if (usernameElem) {
            usernameElem.textContent = username || placeholderUsername;
        }

        if (displayNameElem) {
            displayNameElem.textContent = displayName || placeholderUsername;
        }
    }

    function handleBadges(badges) {

        // known as 
        badges.push({
            badge: "https://cdn.discordapp.com/badge-icons/6de6d34650760ba5551a79732e98ed60.png",
            tooltip: "Originally known as Creation's#0001",
        });

        //hypesquad
        badges.push({
            badge: "https://cdn.discordapp.com/badge-icons/3aa41de486fa12454c3761e8e223442e.png",
            tooltip: "HypeSquad Balance",
        });

        badges.push({
            badge: "https://cdn.discordapp.com/badge-icons/6bdc42827a38498929a4920da12695d9.png",
            tooltip: "Active Developer",
        });

        for (const badge of badges) {
            if ((badge && !badge.badge) || !badge.tooltip) continue;

            const badgeImg = document.createElement("img");
            badgeImg.src = badge.badge;
            badgeImg.alt = badge.tooltip;
            badgeImg.title = badge.tooltip;
            badgeImg.classList.add("badge");
            badgeContainer.appendChild(badgeImg);
        }
    }
});