Select Theme Type:
Static Color
Gradient
Image / Gif
`;
document.body.append(themeEditor);
setTimeout(() => {
document.querySelectorAll(".stats-btn__share-btn")[1].querySelector("rect").remove();
const themeTypeSelect = byId("theme-type-select");
const colorTab = byId("theme_editor_color");
const gradientTab = byId("theme_editor_gradient");
const imageTab = byId("theme_editor_image");
const gradientAngleDiv = byId("theme-editor-gradient_angle");
themeTypeSelect.addEventListener("change", function () {
const selectedOption = themeTypeSelect.value;
switch (selectedOption) {
case "Static Color":
colorTab.style.display = "flex";
gradientTab.style.display = "none";
imageTab.style.display = "none";
break;
case "Gradient":
colorTab.style.display = "none";
gradientTab.style.display = "flex";
imageTab.style.display = "none";
break;
case "Image / Gif":
colorTab.style.display = "none";
gradientTab.style.display = "none";
imageTab.style.display = "flex";
break;
default:
colorTab.style.display = "flex";
gradientTab.style.display = "none";
imageTab.style.display = "none";
}
});
const colorInputs = document.querySelectorAll("#theme_editor_color .colorInput");
colorInputs.forEach(input => {
input.addEventListener("input", function () {
const bgColorInput = byId("theme-editor-bgcolorinput").value;
const textColorInput = byId("theme-editor-colorinput").value;
applyColorTheme(bgColorInput, textColorInput);
});
});
const gradientInputs = document.querySelectorAll("#theme_editor_gradient .colorInput");
gradientInputs.forEach(input => {
input.addEventListener("input", function () {
const gColor1 = byId("theme-editor-gcolor1").value;
const gColor2 = byId("theme-editor-g_color").value;
const gTextColor = byId("theme-editor-gcolor2").value;
const gAngle = byId("g_angle").value;
const gradientType = byId("gradient-type").value;
applyGradientTheme(gColor1, gColor2, gTextColor, gAngle, gradientType);
});
});
const imageInputs = document.querySelectorAll("#theme_editor_image .colorInput");
imageInputs.forEach(input => {
input.addEventListener("input", function () {
const imageLinkInput = byId("theme-editor-imagelink").value;
const textColorImageInput = byId("theme-editor-textcolorImage").value;
let img;
if (imageLinkInput == "") {
img = "https://i.ibb.co/k6hn4v0/Galaxy-Example.png"
} else {
img = imageLinkInput;
}
applyImageTheme(img, textColorImageInput);
});
});
const image_preview = byId("image_preview");
const image_link = byId("theme-editor-imagelink");
let isWriting = false;
let timeoutId;
image_link.addEventListener("input", () => {
if (!isWriting) {
isWriting = true;
} else {
clearTimeout(timeoutId);
}
timeoutId = setTimeout(() => {
const imageLinkInput = image_link.value;
const textColorImageInput = byId("theme-editor-textcolorImage").value;
let img;
if (imageLinkInput === "") {
img = "https://i.ibb.co/k6hn4v0/Galaxy-Example.png";
} else {
img = imageLinkInput;
}
applyImageTheme(img, textColorImageInput);
isWriting = false;
}, 1000);
});
const gradientTypeSelect = byId("gradient-type");
const angleInput = byId("g_angle");
gradientTypeSelect.addEventListener("change", function () {
const selectedType = gradientTypeSelect.value;
gradientAngleDiv.style.display = selectedType === "linear" ? "flex" : "none";
const gColor1 = byId("theme-editor-gcolor1").value;
const gColor2 = byId("theme-editor-g_color").value;
const gTextColor = byId("theme-editor-gcolor2").value;
const gAngle = byId("g_angle").value;
applyGradientTheme(gColor1, gColor2, gTextColor, gAngle, selectedType);
});
angleInput.addEventListener("input", function () {
const gradient_angle_text = byId("gradient_angle_text");
gradient_angle_text.innerText = `Angle (${angleInput.value}deg): `;
const gColor1 = byId("theme-editor-gcolor1").value;
const gColor2 = byId("theme-editor-g_color").value;
const gTextColor = byId("theme-editor-gcolor2").value;
const gAngle = byId("g_angle").value;
const gradientType = byId("gradient-type").value;
applyGradientTheme(gColor1, gColor2, gTextColor, gAngle, gradientType);
});
function applyColorTheme(bgColor, textColor) {
const previewDivs = document.querySelectorAll("#theme_editor_color .themes_preview");
previewDivs.forEach(previewDiv => {
previewDiv.style.backgroundColor = bgColor;
const textSpan = previewDiv.querySelector("span.text");
textSpan.style.color = textColor;
});
}
function applyGradientTheme(gColor1, gColor2, gTextColor, gAngle, gradientType) {
const previewDivs = document.querySelectorAll("#theme_editor_gradient .themes_preview");
previewDivs.forEach(previewDiv => {
const gradient = gradientType === "linear"
? `linear-gradient(${gAngle}deg, ${gColor1}, ${gColor2})`
: `radial-gradient(circle, ${gColor1}, ${gColor2})`;
previewDiv.style.background = gradient;
const textSpan = previewDiv.querySelector("span.text");
textSpan.style.color = gTextColor;
});
}
function applyImageTheme(imageLink, textColor) {
const previewDivs = document.querySelectorAll("#theme_editor_image .themes_preview");
previewDivs.forEach(previewDiv => {
previewDiv.style.backgroundImage = `url('${imageLink}')`;
const textSpan = previewDiv.querySelector("span.text");
textSpan.style.color = textColor;
});
}
const createTheme = byId("createTheme");
createTheme.addEventListener("click", () => {
themeEditor.style.display = "block";
});
const closeThemeEditor = byId("closeThemeEditor");
closeThemeEditor.addEventListener("click", () => {
themeEditor.style.display = "none";
});
let themesDiv = byId("themes")
const saveColorThemeBtn = byId("saveColorTheme");
const saveGradientThemeBtn = byId("saveGradientTheme");
const saveImageThemeBtn = byId("saveImageTheme");
saveColorThemeBtn.addEventListener("click", () => {
const name = byId("colorThemeName").value;
const bgColorInput = byId("theme-editor-bgcolorinput").value;
const textColorInput = byId("theme-editor-colorinput").value;
if (name == "") return
const theme = {
name: name,
background: bgColorInput,
text: textColorInput
};
const themeCard = document.createElement("div");
themeCard.classList.add("theme");
let themeBG;
if (theme.background.includes("http")) {
themeBG = `background: url(${theme.preview || theme.background})`;
} else {
themeBG = `background: ${theme.background}`;
}
themeCard.innerHTML = `
All challenges completed.
`;
} else {
challenges = allChallenges
.filter(({status}) => !status)
.map(({task, best, status, ready, goal}) => {
const desc = shopLocales.challenge_tab.tasks[task].replace(
'%n',
task === 'alive' ? goal / 60 : goal
);
const btn = ready
? `${shopLocales.challenge_tab.result}${Math.round(best)}${task === 'alive' ? 's' : ''}
`;
return `
No messages for today! Be the first one to write one.
`;
return;
}
const messageHTML = messages
.map(message => {
const myMessage = message.user._id === myId;
const imageURL = message.user.imageURL || 'https://app.czrsd.com/static/sigmod_profile.png';
const username = message.user.username || 'Unknown User';
const content = message.content || '';
const timestamp = message.timestamp ? prettyTime.am_pm(message.timestamp) : '';
return `
${messageHTML.length > 0 ? messageHTML : "
Couldn't get messages... Please try again later! "}
`;
if (scrollToBottom) {
const messagesDiv = container.querySelector(".global-chat-content");
messagesDiv.scrollTop = messagesDiv.scrollHeight;
}
}
},
updateModChat(data) {
const {_id: messageId, timestamp, content, user} = data;
const {_id: userId, username, imageURL} = user;
let chatDiv = document.querySelector(".global-chat-content");
if (!chatDiv) {
return;
}
const myMessage = userId === this.profile._id;
chatDiv.innerHTML += `
${history.length > 0 ? messagesHTML : "
This is the beginning of your conversation... "}
`;
body.appendChild(chatDiv);
const messagesContainer = chatDiv.querySelector(".private-chat-content");
messagesContainer.scrollTop = messagesContainer.scrollHeight;
const back = byId("back-friends-chat");
back.addEventListener("click", (e) => {
chatDiv.style.opacity = "0";
setTimeout(() => {
chatDiv.remove();
}, 300);
});
const text = byId("private-message-text");
const send = byId("send-private-message");
text.addEventListener("keydown", (e) => {
const key = e.key.toLowerCase();
if (key === "enter") {
sendMessage(text.value, id)
text.value = "";
}
});
send.addEventListener("click", () => {
sendMessage(text.value, id);
text.value = "";
});
function sendMessage(val, target) {
if (!val || val.length > 200) return;
client.send({
type: "private-message",
content: {
text: val,
target,
}
});
}
},
updatePrivateChat(data) {
const {sender_id, target_id, textmessage, timestamp} = data;
let chatDiv = byId(target_id) || byId(sender_id);
if (!chatDiv) {
console.error("Could not find chat div for either sender or target");
return;
}
const messages = chatDiv.querySelector(".friends-chat-messages");
messages.innerHTML += `
`;
content.innerHTML = announcementHTML;
menuContent.appendChild(content);
window.openModTab("announcement-tab");
const back = byId("mod-announcement-back");
back.addEventListener("click", () => {
const mod_home = byId("mod_home");
content.style.opacity = "0";
setTimeout(() => {
content.remove();
mod_home.style.display = "flex";
mod_home.style.opacity = "1";
}, 300);
byId("tab_home_btn").classList.add("mod_selected");
});1
}
},
chart() {
const canvas = byId("sigmod-stats");
const {Chart} = window;
const stats = JSON.parse(localStorage.getItem("game-stats"));
// max values
const statValues = {
timeplayed: [100_000, 150_000, 200_000, 250_000, 300_000, 400_000, 800_000, 1_000_000],
highestmass: [50_000, 100_000, 500_000, 700_000, 1_000_000, 5_000_000],
totaldeaths: [1_000, 2_000, 3_000, 4_000, 5_000, 8_000, 10_000, 30_000, 50_000, 100_000],
totalmass: [500_000, 1_000_000, 2_000_000, 3_000_000, 5_000_000, 10_000_000, 50_000_000, 100_000_000, 500_000_000, 1_000_000_000]
};
const getBestValue = (stat, values) => {
for (let value of values) {
if (stat < value) return value;
}
return values[values.length - 1]; // Return the highest value if stat exceeds all specified values
};
const emojiLabels = ["ā²", "š", "š", "š¢"];
const textLabels = ["Time Played", "Highest Mass", "Total Deaths", "Total Mass"];
const data = {
labels: emojiLabels,
datasets: [{
label: "Your Stats",
data: [
stats["time-played"] / getBestValue(stats["time-played"], statValues.timeplayed),
stats["highest-mass"] / getBestValue(stats["highest-mass"], statValues.highestmass),
stats["total-deaths"] / getBestValue(stats["total-deaths"], statValues.totaldeaths),
stats["total-mass"] / getBestValue(stats["total-mass"], statValues.totalmass)
],
backgroundColor: [
'rgba(255, 99, 132, 0.2)',
'rgba(54, 162, 235, 0.2)',
'rgba(255, 206, 86, 0.2)',
'rgba(153, 102, 255, 0.2)'
],
borderColor: [
'rgba(255, 99, 132, 1)',
'rgba(54, 162, 235, 1)',
'rgba(255, 206, 86, 1)',
'rgba(153, 102, 255, 1)'
],
borderWidth: 1
}]
};
const formatLabel = (labelType, actualValue) => {
if (labelType === "Time Played") {
const hours = Math.floor(actualValue / 3600);
const minutes = Math.floor((actualValue % 3600) / 60);
return hours > 0 ? `${hours}h ${minutes}m` : `${minutes}m`;
} else if (labelType === "Highest Mass" || labelType === "Total Mass") {
return actualValue > 999 ? `${(actualValue / 1000).toFixed(1)}k` : actualValue.toString();
} else {
return actualValue.toString();
}
};
const createChart = () => {
try {
new Chart(canvas, {
type: "bar",
data: data,
options: {
indexAxis: "y",
scales: {
x: {
beginAtZero: true,
max: 1,
ticks: {
callback: (value) => `${(value * 100).toFixed(0)}%`
}
}
},
plugins: {
legend: {
display: false
},
tooltip: {
callbacks: {
title: (context) => textLabels[context[0].dataIndex],
label: (context) => {
const dataIndex = context.dataIndex;
const labelType = textLabels[dataIndex];
const actualValue = context.dataset.data[dataIndex] * getBestValue(stats[labelType.toLowerCase().replace(" ", "-")], statValues[labelType.toLowerCase().replace(" ", "")]);
return formatLabel(labelType, actualValue);
}
}
}
}
}
});
} catch (error) {
console.error("An error occurred while rendering the chart:", error);
}
};
createChart();
},
// Color input events & Reset color event handler
colorPicker() {
const colorPickerConfig = {
mapColor: { path: "game.map.color", opacity: false, color: modSettings.game.map.color, default: "#111111" },
borderColor: { path: "game.borderColor", opacity: true, color: modSettings.game.borderColor, default: "#0000ff" },
foodColor: { path: "game.foodColor", opacity: true, color: modSettings.game.foodColor, default: null },
cellColor: { path: "game.cellColor", opacity: true, color: modSettings.game.cellColor, default: null },
nameColor: { path: "game.name.color", opacity: false, color: modSettings.game.name.color, default: "#ffffff" },
gradientNameColor1: { path: "game.name.gradient.left", opacity: false, color: modSettings.game.name.gradient.left, default: "#ffffff", },
gradientNameColor2: { path: "game.name.gradient.right", opacity: false, color: modSettings.game.name.gradient.right, default: "#ffffff" },
chatBackground: { path: "chat.bgColor", opacity: true, color: modSettings.chat.bgColor, default: defaultSettings.chat.bgColor, elementTarget: { selector: ".modChat", property: "background" } },
chatTextColor: { path: "chat.textColor", opacity: true, color: modSettings.chat.textColor, default: defaultSettings.chat.textColor, elementTarget: { selector: ".chatMessage-text", property: "color" } },
chatThemeChanger: { path: "chat.themeColor", opacity: true, color: modSettings.chat.themeColor, default: defaultSettings.chat.themeColor, elementTarget: { selector: ".chatButton", property: "background" } }
};
const { Alwan } = window;
Object.entries(colorPickerConfig).forEach(([selector, { path, opacity, color, default: defaultColor, elementTarget }]) => {
const storagePath = path.split('.');
const colorPickerInstance = new Alwan(`#${selector}`, {
id: `edit-${selector}`,
color: color || defaultColor || "#000000",
theme: "dark",
opacity,
format: "hex",
default: defaultColor,
swatches: ["black", "white", "red", "blue", "green"]
});
const pickerElement = byId(`edit-${selector}`);
pickerElement.insertAdjacentHTML('beforeend', `