import { DEV_NAMES, DEV_BIOS } from './scripts/card-values.js';
/**
* user data
* @constructor
* @param {number} points represents # of points earned by user
*/
export function UserInfo(points){
this.points = points
this.life_time_points = points
}
// index of the card to be displayed
let selected_card = 0;
let card_data = [];
window.addEventListener("DOMContentLoaded", init);
/**
* @description Loads the user's saved cards from local storage.
* @returns {Array} An array of saved card objects.
*/
export function load_cards_from_local() {
const data = localStorage.getItem("card_data");
return data ? JSON.parse(data) : [];
}
/**
* @description Saves an array of cards to local storage.
* @param {Array} cards Array of card objects to save.
* @returns {void}
*/
export function save_cards_to_local(cards) {
localStorage.setItem("card_data", JSON.stringify(cards));
}
/**
* @description Adds a new card or updates the quantity if it already exists.
* If the quantity is positive, it increments or sets the card's quantity.
* If the quantity is negative, it decrements the quantity and removes the card if the total falls to 0 or below.
* If the card doesn't exist and quantity is 0 or negative, it does nothing.
*
* @param {Object} card - The card object to add or update. Must include `name` and `rarity` properties.
* @param {number} [quantity=1] - The number of cards to add (positive) or remove (negative).
* @returns {Object|null} The updated card object, or `null` if the card was removed or not added.
*/
export function add_or_update_card(card, num_cards = 1) {
let cards = load_cards_from_local();
const index = cards.findIndex(c => c.name === card.name && c.rarity === card.rarity);
if (index !== -1) {
cards[index].quantity += num_cards;
if (cards[index].quantity <= 0) {
cards.splice(index, 1);
save_cards_to_local(cards);
return null;
}
} else {
cards.push(card);
}
save_cards_to_local(cards);
return cards[index] || card;
}
/**
* @description Fetches data from the JSON file and returns it as a Promise.
* @param {string} path - The path to the JSON file relative to index.html.
* @returns {Promise} A promise that resolves to the data from the JSON file.
* @throws {Error} If the fetch operation fails.
*/
export async function fetch_data(path) {
try {
const response = await fetch(path);
if (!response.ok) {
throw new Error(`Fetch error! status: ${response.status}`);
}
const data = await response.json();
return data;
} catch (error) {
console.error("Error fetching data:", error);
throw error;
}
}
/**
* @description Fetches unlocked cards from local storage.
* @returns {Array} An array of unlocked cards from local storage.
*/
export function fetch_unlocked_cards() {
const data = localStorage.getItem("card_data");
if (!data) {
return [];
}
const parsed_data = JSON.parse(data);
return parsed_data;
}
/**
*
* @returns {UserInfo} returns the user_Data saved to local storage
*/
export function fetch_user_info(){
const data = localStorage.getItem("user_data");
if (!data) {
return undefined;
}
const parsed_data = JSON.parse(data);
return parsed_data;
}
/**
* @description Saves data to local storage.
* @param {Object} data - The data to save to local storage.
* @param {string} key - The key under which to save the data.
* @returns {void}
*/
export function save_to_local(data, key) {
if (!key) {
return;
}
localStorage.setItem(key, JSON.stringify(data));
}
/**
* @description Creates a new frog-card element and appends it inside the <card-deck>.
* @param {Object} data - The data to set on the frog-card element. Matches card-data.json format.
* @returns {HTMLElement} The created frog-card element.
*/
export function createCard(data) {
const cardDeck = document.querySelector("card-deck");
if (!cardDeck){
return
}
cardDeck.innerHTML = ""; // Clear previous card
const card = document.createElement("frog-card");
card.data = data;
cardDeck.appendChild(card);
}
/**
* @description update user points by the point value. Can be negative or positive
* @param {number} points number to increase or decrease user points by
* @return {boolean} returns true if successful else false. If user has too few points its false
*/
export function update_points(points){
const user_data = fetch_user_info()
if (!user_data || typeof user_data.points !== "number" || typeof points !=="number") {
console.warn("Data is missing or malformed", user_data)
return false;
}
let cur_points = user_data.points;
let life_time_points = user_data.life_time_points;
cur_points += points;
if (points > 0) {
life_time_points += points;
}
user_data.points = cur_points;
user_data.life_time_points = life_time_points;
if (cur_points >= 0) {
save_to_local(user_data,"user_data");
return true;
}
return false;
}
/**
* Initializes the card deck on DOM load.
*/
async function init() {
await fetch_data("./card-data.json");
card_data = fetch_unlocked_cards();
// Only create and show card if we have cards
if (card_data.length > 0) {
createCard(card_data[selected_card]);
}
const fetch_user_data = fetch_user_info();
if (!fetch_user_data){
const user_info = new UserInfo(0);
save_to_local(user_info,"user_data");
}
// Handle view all
const viewAllBtn = document.getElementById("view-all");
if (viewAllBtn) {
viewAllBtn.addEventListener("click", () => {
window.location.href = "grid.html";
});
}
//show contributor cards
const cards = document.querySelectorAll("#contributors .contributors-grid frog-card");
cards.forEach((card, index) => {
const name = DEV_NAMES[index];
console.log("Assigning to frog-card:", name, DEV_BIOS[name]);
if (name) {
card.data = {
name: name,
bio: DEV_BIOS[name],
course: "CSE 110",
rarity: "legendary"
};
}
});
}