diff --git a/README.md b/README.md
index 85ff914..94d8a7f 100644
--- a/README.md
+++ b/README.md
@@ -1,7 +1,7 @@
# DCTS - Direct Communication Through Sockets
![Version](https://img.shields.io/static/v1?label=State&message=Early%20Access&color=orange)
-[Visit our Forum - (Early Release Notes/ Plans) ](https://dcts.chat/)
+[Visit our Forum (Planned Features and more)](https://dcts.chat/)
This project was made with the goal to combine TeamSpeak and Discord. The goal: A platform that looks modern like Discord but runs the server like TeamSpeak. DCTS allows you to run your own Discord Server like a TeamSpeak server, in simple words.
@@ -10,8 +10,7 @@ Since you can host the server yourself you're also the one in control of the dat
## Obfuscated?
-Yes. Its not open source. I dont want my work to be copied but yet i still want people to be able to use it. I'll find a better solution in the future.
-The following update wont be obfuscated anymore. More on it can be read [here](https://dcts.chat/main-forum/open-source-update/#post-61)
+Yes. Its not open source. I dont want my work to be copied but yet i still want people to be able to use it. I'll find a better solution in the future.
diff --git a/chat.js b/chat.js
new file mode 100644
index 0000000..7fde640
--- /dev/null
+++ b/chat.js
@@ -0,0 +1,2621 @@
+console.log("%c" + "WAIT!", "color: #FF0000; -webkit-text-stroke: 2px black; font-size: 72px; font-weight: bold;");
+console.log("%c" + "People can use the console to steal your account xo !", "color: #FF0000; -webkit-text-stroke: 0px black; font-size: 20px; font-weight: bold;");
+
+// IMPORTANT! By default, socket.io() connects to the host that
+// served the page, so we dont have to pass the server url
+var socket = io.connect()
+
+
+var chatlog = document.getElementById("content");
+var channeltree = document.getElementById("channeltree");
+var serverlist = document.getElementById("serverlist");
+var groupbanner = document.getElementById("serverbanner-image");
+var memberlist = document.getElementById("infolist");
+var typingIndicator = document.getElementById("typing-indicator");
+var messageInputBox = document.getElementById("messagebox-content");
+
+var typetimeout;
+
+setupNotify();
+setupPrompt();
+
+/*
+console.log("Current Username: " + getUsername());
+console.log("Current Status: " + getStatus());
+console.log("Current About Me: " + getAboutme());
+console.log("Current ID: " + getID());
+console.log("Current PFP: " + getPFP());
+console.log("Current Banner: " + getBanner());
+console.log("Current Group: " + getGroup());
+console.log("Current Channel: " + getChannel());
+console.log("Current Category: " + getCategory());
+console.log("Current Room: " + getRoom());
+
+ */
+//console.log("Current Token: " + getToken());
+
+
+userJoined();
+
+var blockedData = [];
+var blockedDataCounter = [];
+var bypassElement = [];
+var bypassCounter = [];
+
+// If markdown didnt get converted, this will
+function updateMarkdownLinks(delay) {
+ // await ...
+ var elements = document.querySelectorAll(".message-profile-content p");
+
+ var lengthi = 0;
+ if(elements.length <= 50){
+ lengthi = elements.length;
+ }
+ else{
+ lengthi = 50;
+ }
+
+ for(var i = elements.length; i > (elements.length - lengthi); i--){
+
+ try{
+
+ if(elements[i] != null && elements[i].innerText.length > 0) {
+
+
+ var marked = markdown(elements[i].innerText, elements[i].id);
+
+ if(marked != null && marked != elements[i].innerText){
+
+ if(bypassCounter[elements[i].id] == null){
+ bypassCounter[elements[i].id] = 0;
+ }
+ else{
+
+ if(bypassCounter[elements[i].id] >= 1){
+ bypassElement[elements[i].id] = 1;
+ }
+ bypassCounter[elements[i].id]++;
+ }
+
+ if(bypassElement[elements[i].id] == null){
+ elements[i].innerHTML = marked;
+ setTimeout(() => scrollDown(), 10)
+ }
+ }
+ }
+ }
+ catch (err){
+ console.log(err)
+ }
+
+ }
+
+
+
+ setTimeout(() => updateMarkdownLinks(delay), delay)
+}
+updateMarkdownLinks(2000)// If markdown didnt get converted, this will
+
+function markdown(msg, msgid){
+
+ try{
+
+
+ //msg = msg
+ // //.replace(/\*(.*?)*/gim, '$1 ')
+ // .replace(/__(.*?)__/gim, '$1 ')
+ // .replace(/`(.*?)`/gim, '$1
')
+ // .replace(/´´´(.*?)´´´/gim, '
$1 ')
+ // .replace(/~~(.*)~~/gim, '$1')
+ // .replace(/-(.*)/gim, '$1 ')
+ // .replace(/**(.*)**/gim, '$1 ')
+ // //.replace(/\*(.*)\*/gim, '$1 ');
+
+ if(msg == null){
+ return msg;
+ }
+
+ try{
+
+ var msgUrls = getUrlFromText(msg);
+
+ msgUrls.forEach(url => {
+ if(isURL(url)) {
+ if (isAudio(msg)) {
+ //setTimeout(() => scrollDown(), 10)
+ msg = msg.replace(url, `
+
+
${url.split("/").pop().split("_").pop()}
+
+
+ `);
+ }
+ else if (isImage(url) == true) {
+
+ console.log("is image")
+ //setTimeout(() => scrollDown(), 10)
+ msg = msg.replace(url, `
+
+
`);
+
+ } else if (isVideo(msg) == true) {
+ console.log("Is video")
+ var code = `
+
+ `;
+
+ //setTimeout(() => scrollDown(), 10)
+
+ msg = msg.replace(url, `
+
+ `)
+
+ } else {
+ if (url.toLowerCase().includes("youtube") || url.toLowerCase().includes("youtu.be")) {
+ //setTimeout(() => scrollDown(), 10)
+
+ console.log("Is yt video")
+ msg = msg.replace(url, createYouTubeEmbed(url, msgid))
+ } else {
+ msg = msg.replace(url, `${url} `)
+ //return msg.replaceAll(url, `${url} `)
+ }
+
+ }
+ }
+ });
+
+
+ }
+ catch (Exce){
+ //console.log(Exce)
+ }
+
+ return msg;
+ }
+ catch (Exception){
+ //console.log(Exception);
+ }
+}
+
+// Check if client disconnected
+var disconnected = false;
+var initConnectionCheck = false;
+async function checkConnection(delay) {
+
+ //console.log(socket.connected)
+
+ if(initConnectionCheck == false){
+ notify("Connecting...", "info", 1000);
+
+ if(socket.connected == true){
+ notify("Connected!", "success", 1000);
+ initConnectionCheck = true;
+ }
+ }
+ else{
+ if(socket.connected == false && initConnectionCheck == true){
+ disconnected = true;
+ notify("Connection Lost...", "error", 1000);
+ }
+ else if(socket.connected == true && initConnectionCheck == true && disconnected == true){
+ disconnected = false;
+ notify("Successfully reconnected! Reloading...", "success");
+ setTimeout(() => window.location.reload(), 2000)
+ }
+ }
+
+
+
+ setTimeout(() => checkConnection(delay), delay)
+}
+checkConnection(2000)
+
+
+
+
+function mictest(){
+ var constraints = { audio: true };
+ navigator.mediaDevices.getUserMedia(constraints).then(function(mediaStream) {
+ var mediaRecorder = new MediaRecorder(mediaStream);
+
+ mediaRecorder.start();
+
+ mediaRecorder.onstart = function(e) {
+ //
+ };
+
+ mediaRecorder.ondataavailable = async function(e) {
+ var blob = new Blob([e.data], { 'type' : 'audio/ogg; codecs=opus' });
+ socket.emit("sendVoiceData", {id:getID(), token: getToken(), voice: blob }, function (response) {
+ // response
+ });
+ };
+
+
+ mediaRecorder.onstop = function(e) {
+ //
+ };
+
+ // Start recording
+
+
+ // Stop recording after 5 seconds and broadcast it to server
+ setTimeout(function() {
+ mediaRecorder.stop()
+ }, 10);
+ });
+}
+
+
+async function getMedia(constraints) {
+
+ try {
+ let stream = null;
+
+ stream = await navigator.mediaDevices.getUserMedia(constraints);
+
+ var blob = new Blob([stream], { 'type' : 'audio/ogg; codecs=opus' });
+ socket.emit("sendVoiceData", {id:getID(), token: getToken(), voice: blob }, function (response) {
+ // response
+ });
+
+ console.log(blob);
+ let audio = new Audio();
+ audio.srcObject = stream;
+ audio.play();
+
+
+ } catch(err) {
+ document.write(err)
+ }
+}
+
+//getMedia({ audio: true, video: false })
+
+
+socket.on('receiveVoiceData', function (data) {
+
+ console.log("RE")
+
+ var blob = new Blob([data], { 'type' : 'audio/ogg; codecs=opus' });
+ console.log(blob);
+ var audio = document.createElement('audio'); // document.createElement('audio')
+ audio.src = window.URL.createObjectURL(blob);
+ audio.play();
+
+ //data.play();
+
+ /*
+ let audio = new Audio();
+ audio.srcObject = data;
+ audio.play();
+
+ */
+
+});
+
+
+
+
+// Context Menu Stuff
+const ContextMenu = document.getElementById("context-menu");
+const profile = document.getElementById("context-menu");
+var ContextMenuSelectedMessage;
+
+const scope = document.querySelector("body");
+
+scope.addEventListener("click", (event) => {
+
+ const {clientX: mouseX, clientY: mouseY} = event;
+ var clickedElement = document.elementFromPoint(mouseX, mouseY);
+ var profileContent = document.getElementById("profile_container");
+
+
+
+ if(clickedElement.className == "memberlist-member-info" ||
+ clickedElement.classList.contains("memberlist-img") ||
+ clickedElement.className == "memberlist-container" ||
+ clickedElement.className == "message-profile-img" ||
+ clickedElement.className == "message-profile-info-name" ||
+ clickedElement.className == "memberlist-member-info name" ||
+ clickedElement.className == "memberlist-member-info status" ||
+ clickedElement.className == "mention"
+ ){
+ var userid = clickedElement.id;
+
+ if(clickedElement.className == "mention") { userid = userid.replace("mention-", "")}
+ getMemberProfile(userid, mouseX, mouseY);
+ }
+ else if(clickedElement.className.includes("role") && clickedElement.id.split("-")[0] == "addRole"){
+ // Open Role Menu
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "manageMembers" }, function (response) {
+ if(response.permission == "granted"){
+ showRoleMenu(mouseX, mouseY);
+ addRoleFromProfile(clickedElement.id.split("-")[1])
+ }
+ });
+ }
+ else if(clickedElement.className.includes("role_color")){
+ // Remove role code
+
+ }
+ else{
+
+ if(clickedElement.id == "profile-role-menu" ||
+ clickedElement.id == "role-menu-header" ||
+ clickedElement.id == "role-menu-search-icon" ||
+ clickedElement.id == "role-menu-search-input" ||
+ clickedElement.id == "role-menu-list" ||
+ clickedElement.className == "role-menu-entry" ||
+ clickedElement.className == "role-menu-entry-roleName"
+ ){
+ return;
+ }
+
+ profileContent.style.display = "none";
+ profileContent.innerHTML = "";
+
+ hideRoleMenu()
+ }
+
+
+});
+
+function showRoleMenu(mouseX, mouseY){
+ var roleMenu = document.getElementById("profile-role-menu");
+ roleMenu.style.display = "block"
+ roleMenu.style.top = `${mouseY - roleMenu.offsetHeight}px`
+ roleMenu.style.left = `${mouseX - roleMenu.offsetWidth - 20}px`;
+}
+
+function hideRoleMenu(){
+ var roleMenu = document.getElementById("profile-role-menu");
+ roleMenu.style.display = "none"
+}
+
+scope.addEventListener("contextmenu", (event) => {
+ event.preventDefault();
+
+ const {clientX: mouseX, clientY: mouseY} = event;
+ var clickedElement = document.elementFromPoint(mouseX, mouseY);
+
+ //console.log(clickedElement)
+ //console.log(clickedElement.className)
+
+ ContextMenuSelectedMessage = clickedElement;
+
+
+ var ErrorButtonCode = `onMouseOver="this.style.backgroundColor='#eb5055'; this.style.color='white';"
+ onMouseOut="this.style.backgroundColor='transparent'; this.style.color='#eb5055';"
+ style="color: #eb5055;"`;
+
+ var SuccessButtonCode = `onMouseOver="this.style.backgroundColor='#4ba135'; this.style.color='white';"
+ onMouseOut="this.style.backgroundColor='transparent'; this.style.color='#87de54';"
+ style="color: #87de54;"`;
+
+ var OkButtonCode = `onMouseOver="this.style.backgroundColor='#5d7fe3'; this.style.color='white';"
+ onMouseOut="this.style.backgroundColor='transparent'; this.style.color='#5d7fe3';"
+ style="color: #5d7fe3;"`;
+
+ var WarningButtonCode = `onMouseOver="this.style.backgroundColor='#e38a5d'; this.style.color='white';"
+ onMouseOut="this.style.backgroundColor='transparent'; this.style.color='#e38a5d';"
+ style="color: #e38a5d;"`;
+
+
+ // Entire Message: message-profile-content-message
+ // Single Message: message-profile-content-message
+
+ if(//clickedElement.className == "message-profile-content" ||
+ clickedElement.className == "message-profile-content-message" ){
+
+ var messageid = getMessageId(clickedElement);
+
+ resetContextMenuItem(ContextMenu);
+ /*
+ addContextMenuItem(ContextMenu, "Delete All (Buggy) ",
+ ErrorButtonCode + `onclick="bulkDeleteMessageFromChat('${clickedElement.id}');
+ ContextMenu.classList.remove('visible');
+ "`);
+
+ */
+
+ addContextMenuItem(ContextMenu, "Delete Message",
+ `onclick="deleteMessageFromChat('${clickedElement.id}');
+ ContextMenu.classList.remove('visible');
+ "`);
+ }
+ /*
+ else if(clickedElement.className == "message-profile-content-message-appended" ||
+ clickedElement.className == "iframe-container"){
+
+ var messageid = getMessageId(clickedElement);
+
+ resetContextMenuItem(ContextMenu);
+ addContextMenuItem(ContextMenu, "Delete",
+ `onclick="deleteMessageFromChat('${messageid}');
+ ContextMenu.classList.remove('visible');
+ "`);
+ }
+ */
+ else if(clickedElement.className == "memberlist-member-info" ||
+ clickedElement.classList.contains("memberlist-img") ||
+ clickedElement.className == "memberlist-container" ||
+ clickedElement.className == "message-profile-img" ||
+ clickedElement.className == "memberlist-member-info status" ||
+ clickedElement.className == "memberlist-member-info name" ||
+ clickedElement.className == "message-profile-info-name"
+ ){
+
+ try{
+ var userid = clickedElement.id;
+ console.log("Found userid " + userid);
+
+ resetContextMenuItem(ContextMenu);
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "banMember" }, function (response) {
+ if(response.permission == "granted"){
+ addContextMenuItem(ContextMenu, "Ban User",
+ ErrorButtonCode + `onclick="banUser('${userid}');
+ ContextMenu.classList.remove('visible');
+ "`);
+ }
+ });
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "kickUsers" }, function (response) {
+ if(response.permission == "granted"){
+ addContextMenuItem(ContextMenu, "Kick User",
+ ErrorButtonCode + `onclick="kickUser('${userid}');
+ ContextMenu.classList.remove('visible');
+ "`);
+ }
+ });
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "muteUsers" }, function (response) {
+ if(response.permission == "granted"){
+
+ // check if target user is muted
+ socket.emit("getUserFromId", {id:getID(), token: getToken(), target: userid }, function (response2) {
+
+ console.log(response2)
+
+ if(response2.user.isMuted == 1){
+ addContextMenuItem(ContextMenu, "Unmute User",
+ ErrorButtonCode + `onclick="unmuteUser('${userid}');
+ ContextMenu.classList.remove('visible');
+ "`);
+ }
+ else{
+ addContextMenuItem(ContextMenu, "Mute User",
+ ErrorButtonCode + `onclick="muteUser('${userid}');
+ ContextMenu.classList.remove('visible');
+ "`);
+ }
+ });
+
+ }
+ });
+
+ addContextMenuItem(ContextMenu, "Mention user",
+ OkButtonCode + `onclick="
+ mentionUser('${userid}');
+ ContextMenu.classList.remove('visible');
+ ;
+ "`);
+
+ addContextMenuItem(ContextMenu, "Copy User ID",
+ `onclick="navigator.clipboard.writeText('${userid}');
+ ContextMenu.classList.remove('visible');
+ "`);
+ }
+ catch (e){
+ console.log("Could get user id from context menu:");
+ console.log(e);
+ }
+ }
+ else if(clickedElement.className == "image-embed"){
+
+ resetContextMenuItem(ContextMenu);
+
+ addContextMenuItem(ContextMenu, "Open in new Tab",
+ `onclick="
+ openNewTab('${clickedElement.src}');
+ ContextMenu.classList.remove('visible');
+ "`);
+
+ addContextMenuItem(ContextMenu, "Copy URL",
+ `onclick="
+ navigator.clipboard.writeText('${clickedElement.src}');
+ ContextMenu.classList.remove('visible');
+ "`);
+
+ addContextMenuItem(ContextMenu, "Delete Embed",
+ ErrorButtonCode + `onclick="deleteMessageFromChat('${clickedElement.id}');
+ ContextMenu.classList.remove('visible');
+ "`);
+ }
+ else if(clickedElement.id == "channellist" ||
+ clickedElement.id == "channeltree"
+ ){
+
+ resetContextMenuItem(ContextMenu);
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "manageChannels" }, function (response) {
+ if(response.permission == "denied") { console.log(response); return; }
+ addContextMenuItem(ContextMenu, "Create Category",
+ `onclick="
+ createCategory();
+ ContextMenu.classList.remove('visible');
+ "`);
+
+ addContextMenuItem(ContextMenu, "Sort Channels",
+ OkButtonCode + `onclick="
+ sortChannels();
+ ContextMenu.classList.remove('visible');
+ "`);
+ });
+ }
+ else if(clickedElement.className == "categoryTrigger"){
+
+ resetContextMenuItem(ContextMenu);
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "manageChannels" }, function (response) {
+ if(response.permission == "denied") { return; }
+ addContextMenuItem(ContextMenu, "Create Channel",
+ `onclick="
+ createChannel('${clickedElement.id}');
+ ContextMenu.classList.remove('visible');
+ "`);
+ });
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "manageChannels" }, function (response) {
+ if(response.permission == "denied") { return; }
+ addContextMenuItem(ContextMenu, "Create Category",
+ `onclick="
+ createCategory();
+ ContextMenu.classList.remove('visible');
+ "`);
+
+ });
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "manageChannels" }, function (response) {
+ if(response.permission == "denied") { return; }
+ addContextMenuItem(ContextMenu, "Delete Category",
+ ErrorButtonCode + `onclick="
+ deleteCategory('${clickedElement.id}');
+ ContextMenu.classList.remove('visible');
+ "`);
+ });
+ }
+ else if(clickedElement.className == "channelTrigger"){
+ resetContextMenuItem(ContextMenu);
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "manageChannels" }, function (response) {
+ if(response.permission == "denied") { return; }
+ addContextMenuItem(ContextMenu, "Create Channel",
+ `onclick="
+ createChannel('${clickedElement.id}');
+ ContextMenu.classList.remove('visible');
+ "`);
+ });
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "manageChannels" }, function (response) {
+ if(response.permission == "denied") { return; }
+
+ addContextMenuItem(ContextMenu, "Edit Channel",
+ OkButtonCode + `onclick="
+ editChannel('${clickedElement.id}');
+ ContextMenu.classList.remove('visible');
+ "`);
+ });
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "manageChannels" }, function (response) {
+ if(response.permission == "denied") { return; }
+
+ addContextMenuItem(ContextMenu, "Delete Channel",
+ ErrorButtonCode +`onclick="
+ deleteChannel('${clickedElement.id}');
+ ContextMenu.classList.remove('visible');
+ "`);
+ });
+ }
+ else if(clickedElement.id == "serverlist"){
+
+ resetContextMenuItem(ContextMenu);
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "createGroup" }, function (response) {
+ if(response.permission == "denied") { return; }
+ addContextMenuItem(ContextMenu, "Create Group",
+ `onclick="
+ createGroup();
+ ContextMenu.classList.remove('visible');
+ "`);
+ });
+ }
+ else if(clickedElement.classList.contains("server-icon")){
+
+ resetContextMenuItem(ContextMenu);
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: ["manageServer",
+ "manageGroup",
+ "manageChannels",
+ "manageUploads",
+ "manageGroup",
+ "viewLogs",
+ "manageEmojis",
+ "manageBans",
+ "manageServerInfo",
+ "manageRateSettings"]
+ }, function (response) {
+ if(response.permission == "denied") { return; }
+ addContextMenuItem(ContextMenu, "Server Settings",
+ OkButtonCode + `onclick="
+ editServer();
+ ContextMenu.classList.remove('visible');
+ "`);
+
+ addContextMenuItem(ContextMenu, "Edit Group",
+ OkButtonCode + `onclick="
+ editGroup('${clickedElement.id}');
+ ContextMenu.classList.remove('visible');
+ "`);
+
+ if(response.permission == "denied") { return; }
+ addContextMenuItem(ContextMenu, "Delete Group",
+ ErrorButtonCode + `onclick="
+ deleteGroup('${clickedElement.id}');
+ ContextMenu.classList.remove('visible');
+ "`);
+
+ addContextMenuItem(ContextMenu, "Change Icon",
+ `onclick="
+ changeGroupIcon('${clickedElement.id}');
+ ContextMenu.classList.remove('visible');
+ "`);
+ });
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "redeemKey" }, function (response) {
+ if(response.permission == "denied") { return; }
+
+ addContextMenuItem(ContextMenu, "Redeem Key",
+ `onclick="
+ redeemKey();
+ ContextMenu.classList.remove('visible');
+ "`);
+
+ });
+ }
+ else if(clickedElement.id == "serverbanner-image"){
+
+ resetContextMenuItem(ContextMenu);
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "manageServer" }, function (response) {
+ if(response.permission == "denied") { return; }
+ addContextMenuItem(ContextMenu, "Edit Server",
+ `onclick="
+ editServer();
+ ContextMenu.classList.remove('visible');
+ "`);
+ });
+
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "manageGroups" }, function (response) {
+ if(response.permission == "denied") { return; }
+ addContextMenuItem(ContextMenu, "Change Banner",
+ `onclick="
+ changeGroupBanner();
+ ContextMenu.classList.remove('visible');
+ "`);
+ });
+ }
+ else{
+ resetContextMenuItem(ContextMenu);
+ }
+
+ if((ContextMenu.offsetHeight*4) + mouseY > document.body.offsetHeight){
+ ContextMenu.style.top = `${mouseY - ContextMenu.offsetHeight}px`;
+ ContextMenu.style.left = `${mouseX}px`;
+ console.log("is out of bounds")
+ }
+ else{
+ ContextMenu.style.top = `${mouseY}px`;
+ ContextMenu.style.left = `${mouseX}px`;
+ console.log("is not out of bounds")
+ }
+
+
+ ContextMenu.classList.add("visible");
+
+});
+
+scope.addEventListener("click", (e) => {
+
+ if (e.target.offsetParent != ContextMenu) {
+ ContextMenu.classList.remove("visible");
+ }
+});
+
+function editGroup(id){
+ window.location.href = "/settings/group?id=" + id;
+}
+
+function mentionUser(id){
+ messageInputBox.value += ` <@${id}> `;
+ messageInputBox.focus();
+}
+
+function editChannel(channelId){
+ window.location.href = "/settings/channel?id=" + channelId;
+}
+
+function getMemberProfile(id, x, y){
+ //console.log("Requesting profile")
+ socket.emit("getMemberProfile", { id: getID(), token: getToken(), target: id, posX: x, posY: y });
+}
+
+function editServer(){
+ window.location.href = "settings/server/";
+}
+function sortChannels(){
+ window.location.href = "/settings/server/?page=channeltree-sorting";
+}
+
+function redeemKey(){
+ var catname = prompt("Enter the key you want to redeem");
+
+ if(catname == null ||catname.length <= 0){
+ return;
+ }
+ else{
+ socket.emit("redeemKey", { id: getID(), value: catname, token: getToken() });
+ }
+}
+
+function changeGroupIcon(id){
+ var catname = prompt("Group Icon URL:");
+
+ if(catname == null ||catname.length <= 0){
+ return;
+ }
+ else{
+ socket.emit("updateGroupIcon", { id: getID(), value: catname, token: getToken(), group: id });
+ }
+}
+
+function changeGroupBanner(){
+ var catname = prompt("Group Banner URL:");
+
+ if(catname == null ||catname.length <= 0){
+ return;
+ }
+ else{
+ socket.emit("updateGroupBanner", { id: getID(), value: catname, token: getToken(), group: getGroup() });
+ }
+}
+
+function createGroup(){
+ var catname = prompt("Group Name:");
+
+ if(catname == null ||catname.length <= 0){
+ return;
+ }
+ else{
+ socket.emit("createGroup", { id: getID(), value: catname, token: getToken() });
+ }
+}
+
+function openNewTab(url){
+ window.open(url, '_blank');
+}
+
+function createCategory(){
+ var catname = prompt("Category Name:");
+
+ if(catname == null ||catname.length <= 0){
+ console.log("No name?")
+ return;
+ }
+ else{
+ socket.emit("createCategory", { id: getID(), value: catname, token: getToken(), group: getGroup() });
+ }
+}
+
+
+function createChannel(category){
+ var catname = prompt("Channel Name:");
+
+ if(catname == null ||catname.length <= 0){
+ return;
+ }
+ else{
+ socket.emit("createChannel", { id: getID(), value: catname, token: getToken(), group: getGroup().replace("group-", ""), category: category.replace("category-", "")});
+ }
+}
+
+function deleteChannel(id){
+ console.log(id);
+ socket.emit("deleteChannel", { id: getID(), token: getToken(), channelId: id, group: getGroup().replace("group-", "")});
+}
+
+function deleteGroup(groupid){
+ socket.emit("deleteGroup", { id: getID(), token: getToken(), group: groupid });
+}
+
+
+function deleteCategory(id){
+ socket.emit("deleteCategory", { id: getID(), token: getToken(), group: getGroup(), category: id});
+}
+
+function getMessageId(element){
+
+ if(element.className != "message-profile-content-message-appended"){
+ var entireElement = null;
+ element = element.closest(".message-container");
+ return element.id;
+ }
+ else{
+ return element.id;
+ }
+
+
+}
+
+function resetContextMenuItem(element){
+ element.innerHTML = "";
+}
+
+function addContextMenuItem(element, displayname, onclick = ""){
+ var code = `${displayname}
`;
+ element.innerHTML += code;
+}
+
+
+
+function kickUser(id){
+ var reason = prompt("Reason: (empty for none)");
+ socket.emit("kickUser", { id: getID(), token: getToken(), target: id, reason: reason });
+}
+
+function banUser(id){
+ var reason = prompt("Reason: (empty for none)");
+ var duration = prompt("Duration in days: (empty for permanent)");
+ socket.emit("banUser", { id: getID(), token: getToken(), target: id, reason: reason, time: duration });
+}
+
+function muteUser(id){
+ var reason = prompt("Reason: (empty for none)");
+ var duration = prompt("Duration in minutes: (empty for permanent until unmuted)");
+ socket.emit("muteUser", { id: getID(), token: getToken(), target: id, reason: reason, time: duration });
+}
+
+function unmuteUser(id){
+ socket.emit("unmuteUser", { id: getID(), token: getToken(), target: id });
+}
+
+function getChannelTreeSocket(){
+ socket.emit("getChannelTree", { id: getID() , token: getToken(), username: getUsername(), icon: getPFP(), group: getGroup() }, function (response) {
+ channeltree.innerHTML = response.data;
+
+ try{
+ document.querySelector("div #channeltree #channel-" + getChannel()).style.color = "white";
+ document.querySelector("div #channeltree #category-" + getCategory()).style.color = "white";
+
+ var markedMessage3 = [];
+ markedMessage3= getCookie("unmarkedMessages");
+
+ //console.log(markedMessage3);
+ }
+ catch(Ex){
+ //console.log(Ex)
+ }
+ });
+}
+
+function userJoined(){
+ if(getUsername() != null) {
+ var username = getUsername();
+
+ socket.emit("userConnected", { id: getID(), name: username, icon: getPFP(), status: getStatus(), token: getToken(),
+ aboutme: getAboutme(), banner: getBanner()});
+
+ socket.emit("setRoom", { id: getID(), room: getRoom(), token: getToken()});
+ socket.emit("getGroupBanner", { id: getID(), token: getToken() , username: getUsername(), icon: getPFP(), group: getGroup() });
+ socket.emit("getGroupList", { id: getID() , group: getGroup(), token: getToken(), username: getUsername(), icon: getPFP() });
+ socket.emit("getMemberList", { id: getID() , token: getToken(), channel: getChannel(), group: getGroup(), username: getUsername(), icon: getPFP() });
+ getChannelTreeSocket()
+ socket.emit("getCurrentChannel", { id: getID() , token: getToken(), username: getUsername(), icon: getPFP(), group: getGroup(), category: getCategory(), channel: getChannel() });
+ socket.emit("setRoom", { id: getID(), room: getRoom(), token: getToken()});
+
+ getServerInfo();
+
+ getChatlog();
+
+ /*
+ try{
+ var url = window.location.search;
+ var urlParams = new URLSearchParams(url);
+ console.log(url);
+
+ var currentGroup = urlParams.get("group");
+ var currentChannel = urlParams.get("channel");
+ var currentCategory = urlParams.get("category");
+ }
+
+ */
+ }
+ else{
+ console.log("gay")
+ }
+}
+
+window.onunload = (event) => {
+ socket.emit("userDisconnected", { id: getID(), time: new Date().getTime() });
+};
+
+function setTyping(){
+ socket.emit("isTyping", { id: getID(), token: getToken(), room: getRoom() });
+
+
+ clearTimeout(typetimeout);
+ typetimeout = setTimeout(() => {
+
+ socket.emit("stoppedTyping", { id: getID(), token: getToken(), room: getRoom() });
+
+ }, 2 * 1000);
+
+
+}
+
+function getRoom(){
+ return getUrlParams("group") + "-" + getUrlParams("category") + "-" + getUrlParams("channel");
+}
+
+function getUrlParams(param){
+ var url = window.location.search;
+ var urlParams = new URLSearchParams(url);
+ var urlChannel = urlParams.get(param);
+
+ return urlChannel;
+}
+
+function changeUsername(){
+ var username = prompt("What should your new username be?", getUsername());
+
+ if(username.length > 0){
+ setCookie("username", username, 360);
+ updateUsernameOnUI(username, true);
+ }
+ else{
+ alert("Your username was too short");
+ }
+}
+
+function changeStatus(){
+ var status = prompt("What should your new status be?", getStatus());
+
+ if(status.length > 0){
+ setCookie("status", status, 360);
+ updateStatusOnUI(status, true);
+ }
+ else{
+ alert("Your status was too short");
+ }
+}
+
+function changePFP(){
+ var pfp = prompt("Enter the url of your new pfp", getPFP());
+
+ if(pfp.length > 0){
+ setCookie("pfp", pfp, 360);
+ updatePFPOnUI(pfp, true);
+
+ console.log("Letting Server know pfp changed");
+ }
+ else{
+
+ var reset = confirm("Your pfp url was too short. Want to reset your pfp?");
+
+ if(reset){
+ pfp = "/img/default_pfp.png";
+ setPFP(pfp);
+ }
+ else{
+ return;
+ }
+ }
+
+ if(pfp == null || isImage(pfp) == false){
+ pfp = "https://wallpapers-clan.com/wp-content/uploads/2022/05/cute-pfp-25.jpg";
+ }
+
+ setCookie("pfp", pfp, 360);
+ updatePFPOnUI(pfp, true);
+}
+
+function updateUsernameOnUI(username, sync = false){
+ document.getElementById("profile-qa-info-username").innerText = username;
+
+ if(sync == true){
+ socket.emit("setUsername", { id: getID() , username: getUsername(), icon: getPFP() });
+ }
+
+}
+
+function updateStatusOnUI(status, sync = false){
+ document.getElementById("profile-qa-info-status").innerText = status;
+
+ if(sync == true){
+ socket.emit("setStatus", { id: getID() , username: getUsername(), icon: getPFP(), status: getStatus() });
+ }
+}
+
+function updatePFPOnUI(url, sync = false){
+ document.getElementById("profile-qa-img").src = url;
+
+ if(sync == true){
+ socket.emit("setPFP", { id: getID() , username: getUsername(), icon: getPFP() });
+ }
+}
+
+function getChatlog(){
+ socket.emit("getChatlog", { id: getID(), token: getToken(), group: getGroup(), category: getCategory(), channel: getChannel()});
+}
+
+function createYouTubeEmbed(url, messageid){
+
+ var videocode = url.replace("https://www.youtube.com/watch?v=", "").replaceAll(" ", "");
+ if (url.toLowerCase().includes("youtube")) {
+ videocode = url.replace("https://www.youtube.com/watch?v=", "").replaceAll(" ", "");
+ }
+ else if(url.toLowerCase().includes("youtu.be")){
+ videocode = url.replace("https://youtu.be/", "").replaceAll(" ", "");
+ }
+
+ var code = `
VIDEO
`;
+
+ /*
+ console.log("Resolving YouTube URL " + url);
+ console.log("Resolved: " + videocode);
+ console.log("Resolved URL: " + "https://www.youtube.com/embed/" + videocode);
+
+ */
+ return code;
+
+}
+
+
+var notAImage = []
+var notAImageCount = []
+var validImage = []
+function isImage(url){
+
+ const img = new Image();
+
+ /*
+ if(notAImage.includes(url)){
+ console.log("Not a Image")
+ return false;
+ }
+
+ if(validImage.includes(url)){
+ return true;
+ }
+
+ */
+
+ //console.log("checking link " + url)
+
+ img.src = url;
+
+
+ if(img.height > 0 && img.width > 0){
+ if(validImage.includes(url) == false){
+ validImage.push(url);
+ }
+
+
+ return true;
+ }
+ else{
+
+ // Try to load a image 6 times
+ if(notAImage.includes(url) == false && notAImageCount[url] > 6){
+ notAImage.push(url);
+ }
+
+ notAImageCount[url]++;
+ return false;
+ }
+}
+
+function isAudio(url) {
+ return /\.(mp3|wav|ogg)$/.test(url);
+}
+
+function isVideo(url) {
+
+
+ return /\.(mp4|webp)$/.test(url);
+ /*
+ const vid = new HTMLVideoElement();
+ vid.src = url;
+ vid.load();
+
+
+ if(vid.height > 0 && vid.width > 0){
+ return true;
+ }
+ else{
+ return false;
+ }
+
+ */
+}
+
+function getUrlFromText(text){
+ var geturl = new RegExp(
+ "(^|[ \t\r\n])((ftp|http|https|mailto|file):(([A-Za-z0-9$_.+!*(),;/?:@&~=-])|%[A-Fa-f0-9]{2}){2,}(#([a-zA-Z0-9][a-zA-Z0-9$_.+!*(),;/?:@&~=%-]*))?([A-Za-z0-9$_+!*();/?:~-]))"
+ ,"g"
+ );
+ return text.match(geturl)
+}
+
+var isValidUrl = []
+function isURL(text){
+ try {
+
+ const url = new URL(text);
+ return url.protocol === 'http:' || url.protocol === 'https:' || url.protocol == "data:";
+
+
+ } catch (err) {
+ return false;
+ }
+}
+
+function generateMetaTags(){
+ getServerInfo();
+
+ if(getGroup() != null && getCategory() != null && getChannel() != null){
+ return `
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Chat in General » chat `
+ }
+}
+
+function getGroup(){
+
+ var url = window.location.search;
+ var urlParams = new URLSearchParams(url);
+ var urlChannel = urlParams.get("group");
+
+ if(urlChannel == null){
+ return "0";
+ }
+ else{
+ return urlChannel;
+ }
+}
+
+function getCategory(){
+
+ var url = window.location.search;
+ var urlParams = new URLSearchParams(url);
+ var urlChannel = urlParams.get("category");
+
+ if(urlChannel == null){
+ return null;
+ }
+ else{
+ return urlChannel;
+ }
+}
+
+function getChannel(){
+
+ var url = window.location.search;
+ var urlParams = new URLSearchParams(url);
+ var urlChannel = urlParams.get("channel");
+
+ if(urlChannel == null){
+ return null;
+ }
+ else{
+ return urlChannel;
+ }
+}
+
+function getToken(){
+ var token = getCookie("token");
+
+ if(token == null || token.length <= 0){
+ return null;
+ }
+ else{
+ return token;
+ }
+}
+
+function getID(){
+ var id = getCookie("id");
+
+ if(id == null || id.length != 12){
+ id = generateId(12);
+ setCookie("id", id, 360);
+ return id;
+ }
+ else{
+ return id;
+ }
+}
+
+function getPFP(){
+ var pfp = getCookie("pfp");
+
+ if(pfp == null || pfp.length <= 0){
+ pfp = prompt("Please enter the url to your profile picture.");
+
+ if(pfp.length <= 0){
+ pfp = "/img/default_pfp.png";
+ }
+ setCookie("pfp", pfp, 360);
+ updatePFPOnUI(pfp);
+ return pfp;
+ }
+
+ updatePFPOnUI(pfp);
+ return pfp;
+}
+
+function getStatus(){
+ var status = getCookie("status");
+
+ if(status == null || status.length <= 0){
+ setCookie("status", "Hey im new!", 360);
+ updateStatusOnUI(status);
+ return status;
+ }
+ else{
+ updateStatusOnUI(status);
+ return status;
+ }
+}
+
+function getUsername(){
+ var username = getCookie("username");
+
+ if(username == null || username.length <= 0){
+ username = prompt("Whats your username?");
+
+ if(username.length > 0){
+ setCookie("username", username, 360);
+ updateUsernameOnUI(username);
+ return username;
+ }
+ }
+ else{
+ updateUsernameOnUI(username);
+ return username;
+ }
+}
+
+function getAboutme(){
+ var aboutme = getCookie("aboutme");
+
+ if(aboutme == null || aboutme.length <= 0){
+
+ return "";
+ }
+ else{
+ //updateUsernameOnUI(aboutme);
+ return aboutme;
+ }
+}
+
+function getBanner(){
+ var banner = getCookie("banner");
+
+ if(banner == null || banner.length <= 0){
+ return "";
+ }
+ else{
+ //updateUsernameOnUI(aboutme);
+ return banner;
+ }
+}
+
+var lastKey = "";
+var test = 0;
+var testrun = 0;
+function sendMessage(messagebox) {
+
+ //console.log(event.keyCode)
+
+
+ if(event.keyCode != 13){
+ lastKey = event.keyCode;
+ }
+
+ /*
+ if(event.keyCode == 8){
+
+ }
+ */
+
+ // Adding new line
+ if(event.keyCode == 13 && lastKey == 16 && testrun < 6){
+ //document.getElementById("messagebox").style.height = `calc(${document.getElementById("messagebox").offsetHeight}px + 5px) !important;`
+
+ /*document.getElementById("messagebox").offsetHeight +*/
+
+ if(test == 0){
+ test = 44;
+ }
+ else{
+ test += 22;
+ }
+
+ testrun++;
+
+ // Resize message box container
+ document.getElementById('messagebox').setAttribute("style",
+ `
+ height: calc(${test}px - 4px) !important;
+ margin-top: -${test}px !important;
+ `);
+
+
+ // Resize message box input
+ // height: calc(${messageInputBox.offsetHeight}px + 10px) !important;
+ messageInputBox.setAttribute("style",
+ `
+ height: calc(100% - 4px)!important;
+ margin-top: 0.01px !important;
+ padding-bottom: 4px !important;
+ overflow-y: auto;
+ `);
+ /*
+ height: calc(${messageInputBox.offsetHeight}px + 2px ) !important;
+ margin-top: -16px !important;
+ margin-bottom: -6px !important;
+ padding: 0 !important;
+ */
+
+
+ //document.getElementById("messagebox").style.marginTop = `-40px !important`;
+ }
+
+ if(event.keyCode == 37 || event.keyCode == 38 ||
+ event.keyCode == 39 || event.keyCode == 40){
+ return;
+ }
+
+ if(event.keyCode == 13 && lastKey != 16) {
+ sendMessageToServer(getID(), getUsername(), getPFP(), messagebox.value);
+ messagebox.value = "";
+
+ messageInputBox.setAttribute("style",
+ `
+ padding: 8px;
+ height: calc(20px - 3px);
+ width: calc(100% - 32px - 40px - 25px - 5px);
+ margin: -6px 8px 0 8px;
+ overflow-y: hidden;
+ `);
+
+
+ // Resize message box container
+ document.getElementById('messagebox').setAttribute("style",
+ `
+ height: calc(22px);
+ width: calc(100% - 16px - 16px);
+
+ `);
+
+ setTimeout(() => {
+ messageInputBox.value = ""
+ }, 10);
+
+ test = 0;
+ testrun = 0;
+
+ socket.emit("stoppedTyping", { id: getID(), token: getToken(), room: getRoom() });
+ }
+
+
+ if(messagebox.value != ""){
+ setTyping();
+ }
+
+}
+
+function sendMessageToServer(authorId, authorUsername, pfp, message){
+
+ if(getGroup() == null || getGroup().length <= 0 || getCategory() == null || getCategory().length <= 0 || getChannel() == null || getChannel().length <= 0){
+ notify("Please select a channel first", "warning", null, "normal");
+ //alert("Please select any channel first");
+ return;
+ }
+
+ socket.emit("messageSend", { id: authorId, name: authorUsername, icon: pfp, token: getToken(),
+ message: message, group: getGroup(), category: getCategory(),
+ channel: getChannel(), room: getRoom() });
+}
+
+function resolveMentions(){
+ var mentions = document.querySelectorAll("label.mention")
+
+ if(mentions.length <= 0){
+ return;
+ }
+
+ mentions.forEach(mention => {
+ var userId = getID();
+
+ if(mention.id.replace("mention-", "") == userId){
+ mention.parentNode.style.backgroundColor = "rgba(255, 174, 0, 0.12)";
+ //mention.parentNode.style.borderRadius = "6px";
+ mention.parentNode.style.borderLeft = "3px solid rgba(255, 174, 0, 0.52)";
+ mention.parentNode.style.marginTop = "0px";
+ mention.parentNode.style.width = "calc(100% - 8px)";
+ }
+ else{
+ mention.style.backgroundColor = "transparent";
+ }
+
+ })
+}
+
+function convertMention(text, playSoundOnMention = false){
+
+ try{
+ var doc = new DOMParser().parseFromString(text.message, "text/html").querySelector("label")
+ var userId = getID();
+
+ if(doc.id.replace("mention-", "") == (userId)){
+
+ if(playSoundOnMention == true)
+ {
+ //console.log("PLayed message sound");
+ //console.log(playSoundOnMention)
+ playSound("message", 0.5);
+ }
+ }
+
+ }
+ catch (exe){
+ //console.log(exe)
+ }
+}
+
+socket.on('messageCreate', function (message) {
+ message.message = markdown(message.message, message.messageId);
+
+ // User ' + author.username + ' joined the chat!
' +
+ var messagecode = `
+
+
+
+
+
+ ${message.name}
+ ${new Date(message.timestamp).toLocaleString("narrow")}
+
+
+
+ ${message.message.replaceAll("\n", " ")}
+
+
+
`;
+
+
+ var childDivs = document.getElementById("content").lastElementChild;
+
+ if(childDivs != null){
+
+ // Get Elements
+ const messagecontent = childDivs.getElementsByClassName("message-profile-content");
+ const userid = childDivs.getElementsByClassName("message-profile-info");
+
+ const messageDivs = Array.prototype.filter.call(
+ messagecontent,
+ (messagecontent) => messagecontent.nodeName === "DIV"
+ );
+
+ const authorDivs = Array.prototype.filter.call(
+ userid,
+ (userid) => userid.nodeName === "DIV"
+ );
+
+ if(messagecontent[0] == null){
+ addToChatLog(chatlog, messagecode);
+ return;
+ }
+
+ // Calculate time passed
+ var lastMessage = messagecontent[0].id / 1000;
+
+ var today = new Date().getTime() / 1000;
+ var diff = today - lastMessage;
+ var minutesPassed = Math.round(diff / 60);
+
+ //console.log("Past: " + minutesPassed + " minutes");
+
+ if(authorDivs[0].id == message.id && minutesPassed < 5){
+ messagecontent[0].insertAdjacentHTML("beforeend",
+ `${message.message.replaceAll("\n", " ")}
`
+ //`${message.message}
`
+ );
+ }
+ else{
+ addToChatLog(chatlog, messagecode);
+ }
+ }
+ else{
+ addToChatLog(chatlog, messagecode);
+ }
+
+ convertMention(message, true)
+ resolveMentions();
+ scrollDown();
+});
+
+
+function getLastMessage(time = false){
+ var childDivs = document.getElementById("content").lastElementChild;
+
+ if(childDivs != null) {
+
+
+ // Get Elements
+ var messagecontent = childDivs.getElementsByClassName("message-profile-content");
+ var userid = childDivs.getElementsByClassName("message-profile-info");
+
+
+ var messageDivs = Array.prototype.filter.call(
+ messagecontent,
+ (messagecontent) => messagecontent.nodeName === "DIV"
+ );
+
+ const authorDivs = Array.prototype.filter.call(
+ userid,
+ (userid) => userid.nodeName === "DIV"
+ );
+
+ if(messagecontent[0] == null){
+ return;
+ }
+
+ // Calculate time passed
+ var lastMessage = messagecontent[0].id / 1000;
+
+ var today = new Date().getTime() / 1000;
+ var diff = today - lastMessage;
+ var minutesPassed = Math.round(diff / 60);
+
+ if(time == true){
+ return messagecontent[0].id;
+ }
+ else{
+ return messagecontent[0];
+ }
+ }
+}
+
+function compareTimestamps(stamp1, stamp2){
+ // Calculate time passed
+ var firstdate = stamp1 / 1000;
+
+ var seconddate = stamp2 / 1000;
+ var diff = firstdate - seconddate;
+ var minutesPassed = Math.round(diff / 60);
+
+ return minutesPassed;
+}
+
+
+socket.on('showUserJoinMessage', function (author) {
+
+ // User ' + author.username + ' joined the chat!
' +
+ var message = '' +
+ '
User ' + author.username + ' joined the chat!
' +
+ '
';
+
+ addToChatLog(chatlog, message);
+ scrollDown();
+});
+
+socket.on('updateGroupList', function (author) {
+
+ getGroupList();
+});
+
+function deleteMessageFromChat(id){
+
+ socket.emit("deleteMessage", { id: getID(), token: getToken(), messageId: id.replace("msg-", ""),
+ group: getGroup(), category: getCategory(), channel: getChannel() });
+}
+
+function bulkDeleteMessageFromChat(id){
+
+
+ //var children = [].slice.call(document.getElementById(id));
+ var children = null;
+
+ try{
+ console.log("Trying to get parentnode.")
+ children = document.querySelector(`#${id} p`).parentNode;
+ }
+ catch{
+ console.log("Trying fallback parentnode")
+ children = document.querySelector(`#${id}`).parentNode;
+ }
+
+ //console.log("Child")
+ //console.log(children)
+ children = children.querySelector("p");
+ console.log(children)
+
+ for (var i = 0; i < children.length; i++) {
+ //console.log(children[i]); //second console output
+
+ socket.emit("deleteMessage", { id: getID(), token: getToken(), messageId: children[i].id.replace("msg-", ""),
+ group: getGroup().replace("group-", ""), category: getCategory().replace("category-", ""), channel: getChannel().replace("channel-", "") });
+
+ }
+}
+
+socket.on('receiveDeleteMessage', function (id) {
+
+ console.clear();
+
+ //var parent = document.querySelector(`#msg-${CSS.escape(id)}`);
+ //parent.remove();
+ //var container = document.querySelector(`.message-container #${id}`).parentNode.parentNode;
+ //console.log(container)
+
+ console.log(`Deleting from chat #msg-${id}`)
+ console.log(`Scanning for #msg-${id}`)
+ //var parent = document.querySelector(`#msg-${id} p`).parentNode.parentNode;
+
+
+ // document.querySelector(`#msg-152598637369 p`).parentNode;
+ var message = document.querySelectorAll(`div .message-profile-content #msg-${id}`);
+ var parentContainer = message[0].parentNode.parentNode;
+ var parent = message[0].parentNode;
+
+
+ console.log("Message is:")
+ console.log(message)
+ message.forEach(msg => {
+ msg.remove();
+ });
+
+ console.log("parent: ")
+ console.log(parent)
+ console.log(parent.children.length)
+
+ if(parentContainer.querySelector(".message-profile-content-message") == null){
+ parentContainer.remove();
+ }
+
+
+});
+
+socket.on('memberTyping', function (members) {
+
+ var runner = 0;
+ var displayUsersText = "";
+
+ if(members.length <= 0){
+ typingIndicator.innerText = "";
+ typingIndicator.style.display = "none";
+ return;
+ }
+
+ if(members.length == 1){
+ displayUsersText += members[0] + " is typing...";
+ }
+ else if(members.length == 2){
+ displayUsersText += members[0] + " and " + members[1] + " are typing...";
+ }
+ else{
+ members.forEach(member => {
+
+ // Show multiple typing
+ if(runner <= 2){
+ displayUsersText += member + ", ";
+ }
+ runner++;
+ });
+ }
+
+ if(runner > 2){
+ displayUsersText += " and " + members.length - 2 + " users are typing";
+ }
+
+ typingIndicator.innerText = displayUsersText;
+ typingIndicator.style.display = "block";
+});
+
+socket.on('receiveChannelTree', function (data) {
+
+ getChannelTreeSocket();
+ return;
+
+ channeltree.innerHTML = data;
+ try{
+ document.querySelector("div #channeltree #channel-" + getChannel()).style.color = "white";
+ document.querySelector("div #channeltree #category-" + getCategory()).style.color = "white";
+
+ var markedMessage3 = [];
+ markedMessage3 = getCookie("unmarkedMessages");
+
+ console.log(markedMessage3);
+ }
+ catch(Ex){
+ //console.log(Ex)
+ }
+
+
+});
+
+socket.on('markChannelMessage', function (data) {
+
+ /*
+ console.log("A new message has been created");
+ console.log(data);
+
+ var group = data.group;
+ var cat = data.category;
+ var chan = data.channel;
+
+ var groupMarkerElement = document.querySelector(`#group-marker-${group}`);
+ groupMarkerElement.style.display = "block";
+
+ var catElement = document.querySelector(`#category-${cat}`);
+ catElement.style.color = "orange";
+
+ var chanElement = document.querySelector(`#channel-${chan}`);
+ chanElement.style.color = "orange";
+
+ */
+
+});
+
+socket.on('receiveChatlog', function (data) {
+
+
+ if(data == null){
+ console.log("Data was null history")
+ return;
+ }
+
+ var previousMessageID = 0;
+ data.forEach(message => {
+
+ if(message.id == "0"){
+ var message = `
+
${message.name} joined the server!
+
`;
+
+ document.getElementById("content").insertAdjacentHTML("beforeend", message);
+ scrollDown();
+ }
+ else{
+ if(compareTimestamps(message.timestamp, getLastMessage(true)) <= 5
+ && previousMessageID == message.id
+ ){
+ message.message = markdown(message.message, message.messageId);
+
+ getLastMessage().insertAdjacentHTML("beforeend", `${message.message}
`);
+ //getLastMessage().insertAdjacentHTML("beforeend", `${message.message}
`);
+ previousMessageID = message.id;
+
+ }
+ else{
+ message.message = markdown(message.message, message.messageId);
+ showMessageInChat(message)
+ previousMessageID = message.id;
+ }
+ }
+
+
+ });
+
+ scrollDown();
+ resolveMentions();
+});
+
+socket.on('createMessageEmbed', function (data) {
+ document.querySelector("#msg-" + data.messageId).innerHTML = data.code;
+ scrollDown();
+});
+
+socket.on('createMessageLink', function (data) {
+ document.querySelector("#msg-" + data.messageId).innerHTML = data.code;
+ scrollDown();
+});
+
+socket.on('receiveCurrentChannel', function (channel) {
+ try{
+ if(channel.name == null){
+ channel.name = "";
+ }
+ setChannelName(channel.name);
+ }
+ catch{
+ setChannelName(" ");
+ }
+});
+
+socket.on('receiveMemberProfile', function (data) {
+ var profileContent = document.getElementById("profile_container");
+ profileContent.innerHTML = data.code;
+
+ profileContent.style.display = "block";
+ profileContent.style.position = "fixed";
+ profileContent.style.zIndex = "10000";
+
+ var winWidth = window.innerWidth;
+ var winHeight= window.innerHeight;
+
+ // If is out of bounds
+
+ /*
+ console.log(winHeight)
+ console.log(data.top);
+ console.log(profileContent.offsetHeight);
+ console.log((profileContent.offsetHeight - data.top));
+
+ */
+
+ if((data.top + profileContent.offsetHeight) <= winHeight){
+ profileContent.style.top = `${data.top}px`;
+ //console.log("first");
+ }
+ else{
+ if(data.top + profileContent.offsetHeight > winHeight){
+ profileContent.style.top = `${data.top - ((data.top + profileContent.offsetHeight) - winHeight) - 20}px`;
+ //console.log("second");
+ }
+ else{
+ profileContent.style.top = `${data.top - (winHeight - profileContent.offsetHeight)}px`;
+ //console.log("second");
+ }
+
+ }
+
+ // If X out of bounds
+ if((data.left + profileContent.offsetWidth) < winWidth){
+ profileContent.style.left = `${data.left + 20}px`;
+ }
+ else{
+ profileContent.style.left = `${data.left - 20 - profileContent.offsetWidth}px`;
+ }
+
+
+
+});
+
+socket.on('receiveMemberList', function (data) {
+ memberlist.innerHTML = data;
+});
+
+socket.on('updateMemberList', function (data) {
+ getMemberList();
+});
+
+socket.on('updateGroupList', function (data) {
+ getGroupList();
+});
+
+socket.on('receiveGroupList', function (data) {
+ serverlist.innerHTML = "";
+ serverlist.innerHTML = data;
+ setActiveGroup(getGroup());
+});
+
+
+socket.on('newMemberJoined', function (author) {
+
+ // User ' + author.username + ' joined the chat!
' +
+ var message = '' +
+ '
' + author.name + ' joined the server!
' +
+ '
';
+
+ addToChatLog(chatlog, message);
+ scrollDown();
+
+ //socket.emit("getChannelTree", { id: getID(), token: getToken(), username: getUsername(), icon: getPFP(), room: getRoom(), group: getGroup() });
+});
+
+socket.on('memberOnline', function (member) {
+
+ // User ' + author.username + ' joined the chat!
' +
+ var message = '' +
+ '
' + member.username + ' is now online!
' +
+ '
';
+
+ addToChatLog(chatlog, message);
+ scrollDown();
+
+ //socket.emit("getChannelTree", { id: getID(), token: getToken(), username: getUsername(), icon: getPFP(), room: getRoom(), group: getGroup() });
+});
+
+socket.on('memberPresent', function (member) {
+ //socket.emit("getChannelTree", { id: member.id, username: member.username, icon: member.pfp });
+ //socket.emit("getChannelTree", { id: getID(), token: getToken(), username: getUsername(), icon: getPFP(), room: getRoom(), group: getGroup() });
+});
+
+socket.on('receiveGifImage', function (response) {
+
+
+ document.getElementById("emoji-entry-container").insertAdjacentHTML("beforeend",
+ ` `
+ ) ;
+});
+
+socket.on('memberOffline', function (member) {
+ var message = '' +
+ '
' + member + ' is now offline!
' +
+ '
';
+
+ addToChatLog(chatlog, message);
+ scrollDown();
+});
+
+socket.on('configUpdate', function () {
+ getChannelTreeSocket()
+});
+
+socket.on('receiveToken', function (data) {
+ setCookie("token", data, 365);
+});
+
+socket.on('modalMessage', function (data) {
+
+ console.log(data);
+
+ var buttonArray = [];
+ Object.keys(data.buttons).forEach(function(button) {
+
+ var buttonText = data.buttons[button].text;
+ var buttonEvents = data.buttons[button].events;
+
+ buttonArray.push([buttonText.toLowerCase(), buttonEvents])
+ });
+
+ for(let i = 0; i < data.buttons.length; i++){
+ console.log("button : " + data.buttons[i])
+ }
+
+ console.log(buttonArray);
+
+ Confirm(data.title, data.message, "info", buttonArray, "confirm").then(result => {
+
+ console.log(result);
+ })
+});
+
+function setActiveGroup(group){
+ if(group == null){
+ return;
+ }
+ document.getElementById(group).classList.add('selectedGroup');
+}
+
+function addRoleFromProfile(userId){
+ socket.emit("getAllRoles", {id:getID(), token: getToken(), group: getGroup(), targetUser: userId }, function (response) {
+ console.log(response)
+
+ var roleList = document.getElementById("profile-role-menu").querySelector("#role-menu-list");
+ roleList.innerHTML = "";
+
+ var roles = response.data
+ Object.keys(roles).forEach(function (role) {
+
+ var roleObj = roles[role]
+
+ console.log(roleObj)
+ var roleId = roleObj.info.id;
+ var roleName = roleObj.info.name;
+ var roleColor = roleObj.info.color;
+ var hasRole = roleObj.info.hasRole;
+
+ var displayChecked = "";
+ if(hasRole == 1){
+ displayChecked = "checked";
+ }
+ else{
+ displayChecked = "";
+ }
+
+ roleList.insertAdjacentHTML("beforeend", ``)
+ });
+
+ });
+}
+
+function checkCheckedRoleMenu(element){
+ socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "manageMembers" }, function (response) {
+ if(response.permission == "granted"){
+ element.checked = !element.checked;
+ var roleId = element.id.split("_")[1];
+ var userId = element.id.split("_")[2];
+
+ if(element.checked == true){
+ // Assign role
+ socket.emit("addUserToRole", {id:getID(), token: getToken(), role: roleId, target: userId }, function (response) {
+
+ if(response.type != "success"){
+ notify(response.type, response.msg)
+ }
+ });
+ }
+ else{
+ // Remove role
+ socket.emit("removeUserFromRole", {id:getID(), token: getToken(), role: roleId, target: userId }, function (response) {
+ if(response.type != "success"){
+ notify(response.type, response.msg)
+ }
+ });
+ }
+ }
+ });
+}
+
+function showModal(data){
+ var modalBox = document.getElementById("modalBox");
+ var modalBoxTitle = document.getElementById("modalBoxTitle");
+ var modalBoxText = document.getElementById("modalBoxText");
+ var modalBoxButtons = document.getElementById("modalBoxButtons");
+
+ var BodyBlur = document.getElementsByTagName('BODY')[0];;
+ // filter: blur(3px);
+ // transform: translateZ(0);
+
+ //BodyBlur.style.filter = "blur(4px)";
+ //BodyBlur.style.transform = "translateZ(0)";
+
+
+ modalBox.removeAttribute("filter");
+ modalBoxTitle.removeAttribute("filter");
+ modalBoxText.removeAttribute("filter");
+
+ modalBox.style.display = "block";
+ modalBoxButtons.innerHTML = "";
+ modalBoxTitle.innerText = data.title.replaceAll("#", "\n");
+ modalBoxText.innerText = data.message.replaceAll("#", "\n");
+
+
+ if(data.buttons != null){
+
+ Object.keys(data.buttons).forEach(function(button) {
+
+ var buttonText = data.buttons[button].text;
+ var buttonEvent = data.buttons[button].events;
+
+ modalBoxButtons.insertAdjacentHTML("beforeend", `${buttonText} `)
+ });
+ }
+
+ if(data.token != null){
+ setCookie("token", data.token, 365);
+ }
+}
+
+function closeModal(){
+ var modalBox = document.getElementById("modalBox");
+ var modalBoxTitle = document.getElementById("modalBoxTitle");
+ var modalBoxText = document.getElementById("modalBoxText");
+
+ modalBox.style.display = "none";
+ modalBoxTitle.innerText = "";
+ modalBoxText.innerText = "";
+}
+
+function importToken(){
+ var token = prompt("Please paste your exported token here.")
+
+ if(token.length != 48){
+ alert("This token was invalid. If you forgot your token please contact the server admin");
+ return;
+ }
+
+ else{
+ alert("Token successfully set!\nPlease save it if you havent already");
+ setCookie("token", token, 365);
+ }
+}
+
+function resetAccount(){
+ var reset = confirm("Do you really want to reset your account? EVERYTHING will be reset.")
+
+ if(reset){
+ setCookie("id", null, 365);
+ setCookie("username", null, 365);
+ setCookie("status", null, 365);
+ setCookie("pfp", null, 365);
+ setCookie("token", null, 365);
+ setCookie("banner", null, 365);
+
+ alert("Your account has been reset. Please refresh the page if you want to continue");
+ }
+}
+
+
+
+document.getElementById("message-actions").onclick = function(e) {
+ // e = Mouse click event.
+ //var rect = e.target.getBoundingClientRect();
+ //var x = e.clientX - rect.left; //x position within the element.
+ //var y = e.clientY - rect.top; //y position within the element.
+ //console.log("Left? : " + x + " ; Top? : " + y + ".");
+
+ var x = e.clientX;
+ var y = e.clientY;
+
+ var emojiBox = document.getElementById("emoji-box-container");
+
+ var clickedElement = document.elementFromPoint(x, y)
+
+ if(clickedElement.id != "message-actions-image" ){
+ return;
+ }
+
+ if(emojiBox.style.display == "block"){
+ closeEmojiBox();
+ }
+ else{
+ emojiBox.style.display = "block";
+ selectEmojiTab(document.getElementById("emoji-box-emojis"))
+ getEmojis()
+
+ var test = document.getElementById("message-actions-image");
+
+
+
+ /*
+ console.log(emojiBox.offsetHeight)
+ emojiBox.style.top = ((test.style.top + (emojiBox.offsetHeight * 2)) - 60) + "px";
+ emojiBox.style.left = ((test.style.left + emojiBox.offsetWidth * 3.1) + "px");
+
+ */
+
+
+ emojiBox.style.top = (y - emojiBox.offsetHeight - 40) + "px";
+ emojiBox.style.left = x - emojiBox.offsetWidth +"px";
+ }
+}
+
+window.addEventListener('resize', function(event){
+ // do stuff here
+
+ var emojiContainer = document.getElementById("emoji-box-container");
+ var profileContainer = document.getElementById("profile_container");
+
+ if(emojiContainer.style.display == "block"){
+ //emojiContainer.style.display = "none";
+ closeEmojiBox()
+ }
+ if(profileContainer.style.display == "block"){
+ profileContainer.style.display = "none";
+ }
+});
+
+document.addEventListener("keydown", (event) => {
+ var emojiContainer = document.getElementById("emoji-box-container");
+ var profileContainer = document.getElementById("profile_container");
+
+ if(event.key == "Escape"){
+ if(emojiContainer.style.display == "block"){
+ //emojiContainer.style.display = "none";
+ closeEmojiBox();
+ }
+ if(profileContainer.style.display == "block"){
+ profileContainer.style.display = "none";
+ }
+ }
+
+
+});
+
+var gifSearchbarInput = document.getElementById("gif-searchbar-input");
+// Execute a function when the user presses a key on the keyboard
+gifSearchbarInput.addEventListener("keypress", function(event) {
+ // If the user presses the "Enter" key on the keyboard
+
+ if (event.key === "Enter") {
+
+ var emojiEntryContainer = document.getElementById("emoji-entry-container");
+ emojiEntryContainer.innerHTML = "";
+
+ // socket.emit
+
+ socket.emit("searchTenorGif", { id:getID(), token: getToken(), search: gifSearchbarInput.value }, function (response) {
+
+ if(response.type == "success") {
+ console.log("Tenor Response");
+ console.log(response)
+ }
+ else{
+ notify(response.msg, "error")
+ }
+ });
+
+ //searchTenor(gifSearchbarInput.value);
+ }
+});
+
+function selectEmojiTab(element){
+ var parentnode = element.parentNode.children;
+ console.log(parentnode)
+
+ for(let i = 0; i < parentnode.length; i++){
+ if(parentnode[i].classList.contains("SelectedTab")){
+ parentnode[i].classList.remove("SelectedTab");
+ }
+ }
+
+ element.classList.add("SelectedTab");
+}
+
+function sendGif(url){
+
+ if(document.getElementById("messagebox-content").value.replaceAll(" ", "").length >= 1){
+ sendMessageToServer(getID(), getUsername(), getPFP(), document.getElementById("messagebox-content").value);
+ }
+
+ sendMessageToServer(getID(), getUsername(), getPFP(), url);
+
+ closeEmojiBox();
+}
+
+function closeEmojiBox(){
+ var emojiContainer = document.getElementById("emoji-box-container");
+ emojiContainer.style.display = "none";
+
+ var gifSearchbarInput = document.getElementById("gif-searchbar-input");
+ gifSearchbarInput.value = "";
+
+ var emojiEntryContainer = document.getElementById("emoji-entry-container");
+ emojiEntryContainer.innerHTML = "";
+
+ var emojiTab = document.getElementById("emoji-box-emojis");
+ var gifTab = document.getElementById("emoji-box-gifs");
+
+ try{
+ emojiTab.classList.add("SelectedTab");
+ gifTab.classList.remove("SelectedTab");
+ }
+ catch(e){ console.log(e) }
+}
+
+
+function changeGIFSrc(url, element){
+ element.src = url;
+}
+
+
+function getGifs(){
+
+ var emojiContainer = document.getElementById("emoji-box-container");
+ var emojiEntryContainer = document.getElementById("emoji-entry-container");
+ var gifSearchbar = document.getElementById("gif-searchbar");
+ var gifSearchbarInput = document.getElementById("gif-searchbar-input");
+
+ gifSearchbar.style.display = "block";
+ gifSearchbarInput.style.display = "block";
+ emojiEntryContainer.style.height = "calc(100% - 18% - 8.1%)";
+ emojiEntryContainer.innerHTML = "";
+ gifSearchbarInput.focus();
+
+}
+
+function getEmojis() {
+ var emojiContainer = document.getElementById("emoji-box-container");
+ var emojiEntryContainer = document.getElementById("emoji-entry-container");
+
+ gifSearchbarInput.style.display = "none";
+
+ socket.emit("getEmojis", { id:getID(), token: getToken() }, function (response) {
+
+ if(response.type == "success"){
+ //settings_icon.value = response.msg;
+ //emojiContainer.innerHTML = "";
+
+
+
+ emojiEntryContainer.innerHTML = "";
+ response.data.forEach(emoji =>{
+
+ var emojiId = emoji.split("_")[1];
+ var emojiName = emoji.split("_")[2].split(".")[0];
+
+
+ var code = `
+
+
+
+
+
`
+
+
+ emojiEntryContainer.insertAdjacentHTML("beforeend", code);
+ })
+
+ //notify(response.msg)
+ }
+ else{
+ notify(response.msg, "error")
+ }
+
+ //console.log(response);
+ });
+}
+
+
+function exportCookies(){
+ var cookieData = document.cookie.split(';').map(function(c) {
+ var i = c.indexOf('=');
+ return [c.substring(0, i), c.substring(i + 1)];
+ });
+
+ copy(JSON.stringify(JSON.stringify(cookieData)));
+}
+
+function importCookies(data){
+ var cookieData = JSON.parse(data);
+ cookieData.forEach(function (arr) {
+ document.cookie = arr[0] + '=' + arr[1];
+ });
+}
+
+function setUser(username){
+ setCookie("username", username, 360);
+ updateUsernameOnUI(username);
+}
+
+function setBanner(banner){
+ setCookie("banner", banner, 360);
+}
+
+function setStatus(status){
+ setCookie("status", status, 360);
+ updateUsernameOnUI(status);
+}
+
+function setPFP(pfp){
+ setCookie("pfp", pfp, 360);
+ updateUsernameOnUI(pfp);
+}
+
+function setAboutme(aboutme){
+ setCookie("aboutme", aboutme, 360);
+ updateUsernameOnUI(aboutme);
+}
+
+socket.on('receiveGroupBanner', function (data) {
+ groupbanner.src = data;
+});
+
+
+function refreshValues(){
+ var username = getUsername();
+ getID();
+ getPFP();
+ getStatus();
+ getGroup();
+ getChannel();
+ getCategory();
+ getRoles();
+ getToken();
+ userJoined();
+ getServerInfo();
+
+ socket.emit("setRoom", { id: getID() , username: getUsername(), icon: getPFP(), room: getRoom(), token: getToken() });
+ getGroupList();
+ getMemberList();
+ getChannelTreeSocket()
+ socket.emit("getCurrentChannel", { id: getID() , username: username, icon: getPFP(), group: getGroup(), category: getCategory(), channel: getChannel(), token: getToken() });
+}
+
+function getMemberList(){
+ socket.emit("getMemberList", { id: getID() , username: getUsername(), icon: getPFP(), token: getToken(), channel: getChannel() });
+}
+
+function getGroupList(){
+ socket.emit("getGroupList", { id: getID() , group: getGroup(), username: getUsername(), icon: getPFP(), token: getToken() });
+ getGroupBanner();
+}
+
+function getGroupBanner(){
+ socket.emit("getGroupBanner", { id: getID() , username: getUsername(), icon: getPFP(), group: getGroup(), token: getToken() });
+}
+
+var serverName;
+var serverDesc;
+function getServerInfo(returnData = false){
+ socket.emit("getServerInfo", {id:getID(), token: getToken() }, function (response) {
+
+ var headline = document.getElementById("header");
+
+ servername = response.name;
+ serverdesc = response.description;
+
+ headline.innerHTML = `${servername} - ${serverdesc}`;
+ });
+}
+
+function setUrl(param){
+
+ window.history.replaceState(null, null, param); // or pushState
+ chatlog.innerHTML = "";
+
+ document.getElementById("messagebox-content").focus();
+
+ refreshValues();
+}
+
+function setChannelName(name){
+ document.getElementById("channelname").innerText = name;
+}
+
+function getRoles(){
+ socket.emit("RequestRoles", { id: getID(), username: getUsername(), pfp: getPFP() });
+}
+
+function generateId(length) {
+ let result = '1';
+ const characters = '0123456789';
+ const charactersLength = characters.length;
+ let counter = 0;
+ while (counter < length-1) {
+ result += characters.charAt(Math.floor(Math.random() * charactersLength));
+ counter += 1;
+ }
+ return result;
+}
+
+function addToChatLog(element, text){
+ //text = markdown(text, null);
+ element.insertAdjacentHTML('beforeend', text);
+ scrollDown();
+}
+
+function scrollDown(){
+ var objDiv = document.getElementById("content");
+ objDiv.scrollTop = objDiv.scrollHeight;
+}
+
+
+
+function upload(files) {
+ socket.emit("fileUpload", {file: files, filename: files.name, id:getID(), token: getToken() }, function (response) {
+
+ if(response.type == "success"){
+ //notify(response.msg, "success")
+ console.log(response);
+
+ //console.log(`sending ${window.location.origin + response.msg}`)
+ sendMessageToServer(getID(), getUsername(), getPFP(), window.location.origin + response.msg);
+ }
+ else{
+ notify(response.msg, "error", null, "normal")
+ }
+ });
+}
+
+
+var uploadObject = document.getElementById('content');
+uploadObject.addEventListener('drop', function (e) {
+ // Code for upload file here
+ e.preventDefault()
+ uploadObject.style.backgroundColor = '#36393F';
+
+ var file = e.dataTransfer.files[0]
+ var fileSize = file.size / 1024 / 1024;
+ console.log(`Size: ${fileSize.toFixed(2)} MB`);
+
+ upload(file);
+
+}, false);
+
+uploadObject.addEventListener('dragenter', function (e) {
+ e.preventDefault();
+
+ uploadObject.style.backgroundColor = 'gray';
+}, false);
+
+uploadObject.addEventListener('dragover', function (e) {
+ e.preventDefault();
+ uploadObject.style.backgroundColor = 'gray';
+}, false);
+
+uploadObject.addEventListener('dragleave', function (e) {
+ e.preventDefault();
+ uploadObject.style.backgroundColor = '#36393F';
+}, false);
+
+
+
+
+
+
+
+function showMessageInChat(message) {
+
+
+ message.message = markdown(message.message, message.messageId)
+
+ var messagecode = `
+
+
+
+
+
+ ${message.name}
+ ${new Date(message.timestamp).toLocaleString("narrow")}
+
+
+
+ ${message.message}
+
+
+
`;
+
+ addToChatLog(chatlog, messagecode);
+ convertMention(message, false)
+ scrollDown();
+}
+function setCookie(name,value,days) {
+ var expires = "";
+ if (days) {
+ var date = new Date();
+ date.setTime(date.getTime() + (days*24*60*60*1000));
+ expires = "; expires=" + date.toUTCString();
+ }
+ document.cookie = name + "=" + (value || "") + expires + "; path=/";
+}
+function getCookie(name) {
+ var nameEQ = name + "=";
+ var ca = document.cookie.split(';');
+ for(var i=0;i < ca.length;i++) {
+ var c = ca[i];
+ while (c.charAt(0)==' ') c = c.substring(1,c.length);
+ if (c.indexOf(nameEQ) == 0) return c.substring(nameEQ.length,c.length);
+ }
+ return null;
+}
+function eraseCookie(name) {
+ document.cookie = name +'=; Path=/; Expires=Thu, 01 Jan 1970 00:00:01 GMT;';
+}
\ No newline at end of file
diff --git a/dcts-shipping.zip b/dcts-shipping.zip
deleted file mode 100644
index 7655a16..0000000
Binary files a/dcts-shipping.zip and /dev/null differ
diff --git a/index.html b/index.html
new file mode 100644
index 0000000..d766c8a
--- /dev/null
+++ b/index.html
@@ -0,0 +1,1311 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Document
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
Shy Devil
+
.gg/femboi
+
+
+
About Me
+
+ sys-admin. programmer.
+
+ Femboy Cartel
+ https://discord.gg/cr82MnSAfT
+
+
+
+
Roles
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ -
+ -
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ -
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
Shy Devil is typing...
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/index.js b/index.js
index ffd495f..5bf6c2e 100644
--- a/index.js
+++ b/index.js
@@ -27,6 +27,8 @@ var request = require('request');
//require('whatwg-fetch')
var usersocket = []
+var userOldRoom = []
+var peopleInVC = {}
var showedOfflineMessage = [];
var typingMembers = [];
@@ -208,7 +210,6 @@ var serverconfig = JSON.parse(fs.readFileSync("./config.json", {encoding: "utf-8
if(serverconfig.serverinfo.ssl.enabled == 1){
- console.log("Yes");
server = https.createServer({
key: fs.readFileSync(serverconfig.serverinfo.ssl.key),
@@ -760,8 +761,66 @@ io.on('connection', function (socket) {
}
});
+ // vc setting
+ socket.on('audioStream', function (member) {
+ if(validateMemberId(member.id, socket) == true
+ && serverconfig.servermembers[member.id].token == member.token
+ ) {
+ peopleInVC[member.room][member.id].lastActivity = new Date().getTime();
+ socket.to(member.room).emit("audioData", {speakingMember: member.id, audioData: member.audioData});
+ }
+ });
+
+ socket.on('joinedVC', function (member) {
+ if(validateMemberId(member.id, socket) == true
+ && serverconfig.servermembers[member.id].token == member.token
+ ) {
+
+ var memberTransmitObj = {id: member.id, name: serverconfig.servermembers[member.id].name, icon: serverconfig.servermembers[member.id].icon, room: member.room, lastActivity: member.lastActivity};
+
+ if(peopleInVC[member.room] == null) peopleInVC[member.room] = {};
+ peopleInVC[member.room][member.id] = memberTransmitObj;
+
+ socket.to(member.room).emit("userJoinedVC", memberTransmitObj);
+ socket.emit("userJoinedVC", memberTransmitObj);
+ }
+ });
+
+ socket.on('leftVC', function (member) {
+ if(validateMemberId(member.id, socket) == true
+ && serverconfig.servermembers[member.id].token == member.token
+ ) {
+ // User already left, so the room id wouldnt be correct anymore
+ member.room = userOldRoom[member.id];
+ try{ delete peopleInVC[member.room][member.id] } catch (error) { console.log("error deleting it"); console.log(error); }
+ socket.to(member.room).emit("userLeftVC", {id: member.id, name: serverconfig.servermembers[member.id].name, icon: serverconfig.servermembers[member.id].icon, room: member.room});
+ }
+ });
+
+ socket.on('getVCMembers', function (member, response) {
+ if(validateMemberId(member.id, socket) == true
+ && serverconfig.servermembers[member.id].token == member.token
+ ) {
+ Object.keys(peopleInVC[member.room]).forEach(function(memberId) {
+ var user = peopleInVC[member.room][memberId];
+ var lastOnline = user.lastActivity / 1000;
+
+ var today = new Date().getTime() / 1000;
+ var diff = today - lastOnline;
+ var minutesPassed = Math.round(diff / 60);
+
+ if(minutesPassed > 0){
+ delete peopleInVC[member.room][memberId];
+ }
+ });
+
+
+ response({type: "success", vcMembers: peopleInVC[member.room]});
+ }
+ });
+
socket.on('redeemKey', function (member) {
if(validateMemberId(member.id, socket) == true
&& serverconfig.servermembers[member.id].token == member.token
@@ -974,6 +1033,24 @@ io.on('connection', function (socket) {
return;
}
+ if(serverconfig.groups[member.group].channels.categories[member.category].channel[member.channel].type == "voice"){
+ sendMessageToUser(socket.id, JSON.parse(
+ `{
+ "title": "You cant chat here",
+ "message": "This is a voice channel",
+ "buttons": {
+ "0": {
+ "text": "Ok",
+ "events": ""
+ }
+ },
+ "type": "error",
+ "popup_type": "confirm"
+ }`));
+
+ return;
+ }
+
var messageid = generateId(12);
member.timestamp = new Date().getTime();
@@ -991,13 +1068,6 @@ io.on('connection', function (socket) {
return
}
-
-
- // Get Emojis (only works with one)
- //const emojiCode = getEmojiCode(member.message, ':', ':');
- //console.log("Emoji Code was " + emojiCode)
-
-
/*
The following performs the same replace function with the only
difference to check if any text is left after converting the emojis.
@@ -1031,19 +1101,6 @@ io.on('connection', function (socket) {
}
});
- /*
- if(emojiCode.length > 0){
- // match(":(.*):")
- var matched = member.message.search(`(:)\\w+`);
- console.log(matched);
-
- member.message = member.message.replaceAll(`(:)\\w+`, ` `);
- }
-
- */
-
-
- //member.message = markdown(member.message, messageid, member.room);
member.token = null;
@@ -1193,7 +1250,13 @@ io.on('connection', function (socket) {
sortedRoles[role].info.hasRole = 0;
}
- returnRole.push(sortedRoles[role]);
+ // Get Highest role of user doing it
+ var executer = getMemberHighestRole(member.id);
+
+ // Only let people show roles they can actually assign
+ if(sortedRoles[role].info.sortId < executer.info.sortId && role != 0 && role != 1){
+ returnRole.push(sortedRoles[role]);
+ }
}
});
@@ -1316,8 +1379,6 @@ io.on('connection', function (socket) {
try {
fs.unlinkSync(`./public/emojis/${member.emoji}`);
-
- console.log("Deleted Emoji successfully.");
response({type: "success", msg: "Emoji deleted successfully"});
} catch (error) {
@@ -1434,6 +1495,27 @@ io.on('connection', function (socket) {
}
}
+ var executer = getMemberHighestRole(member.id);
+ var target = getMemberHighestRole(member.target);
+
+
+ if(executer.info.sortId >= target.info.sortId){
+ sendMessageToUser(socket.id, JSON.parse(
+ `{
+ "title": "Error!",
+ "message": "You cant assign this role because its higher or equal then yours",
+ "buttons": {
+ "0": {
+ "text": "Ok",
+ "events": ""
+ }
+ },
+ "type": "success",
+ "popup_type": "confirm"
+ }`));
+ return;
+ }
+
serverconfig.serverroles[member.role].members.push(member.target);
saveConfig();
@@ -1469,6 +1551,32 @@ io.on('connection', function (socket) {
}
}
+ var executer = getMemberHighestRole(member.id);
+ var target = getMemberHighestRole(member.target);
+
+
+ if(executer.info.sortId <= target.info.sortId){
+ sendMessageToUser(socket.id, JSON.parse(
+ `{
+ "title": "Error!",
+ "message": "You cant remove this role because its higher or equal then yours",
+ "buttons": {
+ "0": {
+ "text": "Ok",
+ "events": ""
+ }
+ },
+ "type": "success",
+ "popup_type": "confirm"
+ }`));
+ return;
+ }
+
+ // Default Roles
+ if(serverconfig.serverroles[member.role].info.id == 0 || serverconfig.serverroles[member.role] == 1){
+ return;
+ }
+
serverconfig.serverroles[member.role].members.pop(member.target);
saveConfig();
@@ -1520,7 +1628,6 @@ io.on('connection', function (socket) {
if(hasPermission(member.id, "manageChannels")){
try{
//console.log(member.role);
- console.log(member.permissions);
var memberChannel = member.channel.replace("channel-", "");
@@ -2336,7 +2443,6 @@ io.on('connection', function (socket) {
if(member.reason.length > 0)
reasonText = `##Reason:#${member.reason}`;
- console.log(member.time)
if(member.time.length == 0){
// You have been muted
@@ -2401,14 +2507,71 @@ io.on('connection', function (socket) {
"popup_type": "confirm"
}`));
+ if(userOldRoom.hasOwnProperty(member.id)){
+ socket.leave(userOldRoom[member.id])
+ }
+
socket.join(0);
+ userOldRoom[member.id] = 0;
return;
}
try{
+ // If the channel exists
if(serverconfig.groups[group].channels.categories[category].channel[channel] != null){
- socket.join(escapeHtml(member.room));
- consolas(`User joined room ${escapeHtml(member.room)}`.green, "Debug");
+
+ // If its a text channel
+ if(serverconfig.groups[group].channels.categories[category].channel[channel].type == "text"){
+
+ // Permission already checked above for text on default
+
+ // Update Room and save previous one
+ if(userOldRoom.hasOwnProperty(member.id)){
+ socket.leave(userOldRoom[member.id])
+ }
+ socket.join(escapeHtml(member.room));
+ userOldRoom[member.id] = escapeHtml(member.room);
+
+ consolas(`User joined text room ${escapeHtml(member.room)}`.green, "Debug");
+ }
+ // If its a voice channel
+ else if(serverconfig.groups[group].channels.categories[category].channel[channel].type == "voice") {
+
+ // If user can use VC
+ if (!checkUserChannelPermission(channel, member.id, "useVOIP")) {
+ sendMessageToUser(socket.id, JSON.parse(
+ `{
+ "title": "Access denied",
+ "message": "You're not allowed to talk in this channel",
+ "buttons": {
+ "0": {
+ "text": "Ok",
+ "events": ""
+ }
+ },
+ "type": "error",
+ "popup_type": "confirm"
+ }`));
+
+ // Update Room and save previous one
+ if (userOldRoom.hasOwnProperty(member.id)) {
+ socket.leave(userOldRoom[member.id])
+ }
+ socket.join(0);
+ userOldRoom[member.id] = 0;
+ return;
+ }
+
+ // Update Room and save previous one
+ if(userOldRoom.hasOwnProperty(member.id)){
+ socket.leave(userOldRoom[member.id])
+ }
+ socket.join(escapeHtml(member.room));
+ userOldRoom[member.id] = escapeHtml(member.room);
+
+ consolas(`User joined VC room ${escapeHtml(member.room)}`.green, "Debug");
+ }
+
}
}
catch(erorr){
@@ -2467,14 +2630,6 @@ io.on('connection', function (socket) {
}
});
- socket.on('sendVoiceData', function (member, response) {
- if(validateMemberId(member.id, socket) == true
- && serverconfig.servermembers[member.id].token == member.token) {
-
- io.emit("receiveVoiceData", member.voice);
- }
- });
-
socket.on('setUsername', function (member) {
if(validateMemberId(member.id, socket) == true
&& serverconfig.servermembers[member.id].token == member.token) {
@@ -2910,7 +3065,7 @@ io.on('connection', function (socket) {
`{
"id": ${channelId},
"name": "${escapeHtml(member.value)}",
- "type": "text",
+ "type": "${member.type}",
"description": "Default Channel Description",
"sortId": 0,
"permissions": {
@@ -3165,7 +3320,7 @@ io.on('connection', function (socket) {
socket.on('getCurrentChannel', function (member) {
if(validateMemberId(member.id, socket) == true) {
- consolas("Resolving Channel ID to Name", "Debug");
+ //consolas("Resolving Channel ID to Name", "Debug");
//console.log(serverconfig.groups[member.group].channels.categories[member.category].channel[member.channel]);
try{
@@ -4782,8 +4937,16 @@ function getChannelTree(member){
if(checkUserChannelPermission(chan.id, member.id, "viewChannel") || hasPermission(member.id, "manageChannels", member.group)){
if(added_channels.includes(chan.id + "_" + chan.name) == false){
- treecode += `${chan.name} `;
- added_channels.push(chan.id + "_" + chan.name)
+
+ // if text channel
+ if(chan.type == "text"){
+ treecode += `⌨ ${chan.name} `;
+ added_channels.push(chan.id + "_" + chan.name)
+ }
+ else if(chan.type == "voice"){
+ treecode += `🎤 ${chan.name} `;
+ added_channels.push(chan.id + "_" + chan.name)
+ }
}
}
@@ -4795,23 +4958,6 @@ function getChannelTree(member){
});
- /*
- if(sortedCats.length == null){
-
- if(hasPermission(member.id, "manageChannels")){
- if(showedCategory == false && addedCategories.includes(groupCategories[category].info.name) == false){
-
- treecode += "";
- treecode += `${groupCategories[category].info.name} `;
- treecode += ``
-
- addedCategories.push(groupCategories[category].info.name)
- }
- }
-
- }
-
- */
treecode += " ";
treecode += " ";
@@ -4907,7 +5053,6 @@ function linkify(text, messageid, roomid) {
} else {
isImgUrl(url).then((result) => {
- console.log("result was " + result);
if (result == true) {
console.log("Returning img embed")
diff --git a/modules/general/redeemKey.cjs b/modules/general/redeemKey.cjs
deleted file mode 100644
index 2c59131..0000000
--- a/modules/general/redeemKey.cjs
+++ /dev/null
@@ -1,5 +0,0 @@
-//const colors = require("colors");
-
-module.exports = function(socket) {
-
-}
\ No newline at end of file
diff --git a/notify.js b/notify.js
new file mode 100644
index 0000000..fc1ac07
--- /dev/null
+++ b/notify.js
@@ -0,0 +1,192 @@
+var notifyBoxTimeout;
+var notifyBoxTimeoutHide;
+function notify(text, icon, duration = 4000, sound = null, reload = null){
+ var notifyBox = document.getElementById("notification-container");
+ var notifyTitle = document.getElementById("notification-container-title");
+ var notifyIcon = document.getElementById("notification-container-icon");
+
+ // Disable fade in out stuff
+ clearTimeout(notifyBoxTimeout);
+ clearTimeout(notifyBoxTimeoutHide);
+
+ notifyBox.style.animation = "fadein 1s";
+ notifyTitle.innerText = text
+
+ notifyIcon.src = "/img/" + icon + ".png";
+ notifyIcon.onerror = () => {
+ notifyIcon.src = "/img/error.png";
+ }
+
+ if(duration == null){
+ duration = 4000;
+ }
+
+ if(sound != null){
+ playSound(sound)
+ }
+
+ if(icon == "error"){
+ notifyBox.style.backgroundColor = "tomato";
+ notifyBox.style.color = "white";
+ }
+ else if(icon == "success"){
+ notifyBox.style.backgroundColor = "#1EDC49";
+ notifyBox.style.color = "white";
+ }
+ else if(icon == "warning"){
+ notifyBox.style.backgroundColor = "#E9B31C";
+ notifyBox.style.color = "white";
+ }
+ else{
+ notifyBox.style.backgroundColor = "#202225";
+ notifyBox.style.color = "white";
+ }
+
+ notifyBox.style.display = "block";
+
+ notifyBoxTimeout = setTimeout(() => {
+ notifyBox.style.animation = "fadeout 1s";
+
+ notifyBoxTimeoutHide = setTimeout(() => {
+ notifyBox.style.display = "none";
+
+
+ if(reload != null){
+ window.location.reload()
+ }
+ }, "800");
+ }, duration);
+}
+
+var audio = new Audio();
+function playSound(sound, volume = 0.1){
+ audio.src = `/sounds/${sound}.mp3`;
+ audio.volume = volume;
+ audio.play();
+}
+
+function setupNotify(){
+ var code = `
+
+
+
+
+
+ Data Successfully Saved
+
+
+
`;
+
+ document.body.insertAdjacentHTML("beforeend", code);
+
+}
+
+
+/*
+
+
+
+
+
+
+
+ Data Successfully Saved
+
+
+
+
+ */
\ No newline at end of file
diff --git a/out.log b/out.log
deleted file mode 100644
index 1bd54bf..0000000
--- a/out.log
+++ /dev/null
@@ -1,171 +0,0 @@
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
-is not running
diff --git a/prompt.css b/prompt.css
new file mode 100644
index 0000000..f4974c6
--- /dev/null
+++ b/prompt.css
@@ -0,0 +1,91 @@
+#prompt-container {
+ background-color: #36393F;
+ color: white;
+ padding: 16px;
+ border-radius: 10px;
+ border: 1px solid #677073;
+ max-width: 50%;
+
+ display: block;
+ justify-content: center;
+
+ position: fixed;
+
+ -webkit-box-shadow: 29px 41px 29px -1px rgba(0,0,0,0.75);
+ -moz-box-shadow: 29px 41px 29px -1px rgba(0,0,0,0.75);
+ box-shadow: 29px 41px 29px -1px rgba(0,0,0,0.75);
+
+ z-index: 99999;
+
+ position: absolute;
+ top: 50%;
+ left: 50%;
+ margin-right: -50%;
+ transform: translate(-50%, -50%);
+
+ animation: fadein 0.5s;
+}
+
+#prompt-content-container {
+ display: flex;
+}
+
+#prompt-img-container {
+ float: left;
+ background-color: transparent;
+ margin: auto;
+ margin-right: 8px;
+ display: block;
+ width: 50px;
+}
+
+#prompt-text-container {
+ float: right;
+ background-color: transparent;
+ /* width: calc(100% - 50px - 16px); */
+ padding: 0 8px 0 8px;
+
+}
+
+#prompt-container #prompt-icon {
+ width: 50px;
+ height: 50px;
+ border-radius: 50%;
+}
+
+#prompt-container #prompt-title {
+ background-color: transparent;
+ display: inline-block;
+ font-weight: bold;
+ margin-top: 0px;
+}
+
+#prompt-container #prompt-text {
+ background-color: transparent;
+ display: block;
+ display: inline-block;
+ margin-bottom: 0;
+ word-break: break-all;
+}
+
+#prompt-input-container input {
+ outline: none;
+ padding: 2px 4px 2px 4px;
+ margin: 4px;
+ background-color: #36393F;
+ color: white;
+ border: 1px solid white;
+ border-radius: 4px;
+}
+
+#prompt-input-container {
+ background-color: transparent;
+ float: left;
+ margin-top: 8px;
+}
+
+#prompt-input-container button {
+ margin-top: 16px;
+ margin-right: 4px;
+ float: left;
+}
\ No newline at end of file
diff --git a/prompt.js b/prompt.js
new file mode 100644
index 0000000..2b46108
--- /dev/null
+++ b/prompt.js
@@ -0,0 +1,221 @@
+var promptBox;
+var promptIcon;
+var promptTitle;
+var promptText;
+
+var promptInputText;
+var promptInputNumber;
+
+var promptInputs;
+var promptInputYes;
+var promptInputNo;
+var promptInputCancel;
+var promptInputOk;
+
+function closePrompt(){
+ //promptBox.style.display = "none";
+
+
+ promptBox.style.animation = "fadeout 0.5s";
+ setTimeout(() => {
+ promptBox.style.display = "none";
+ }, "300");
+
+ setTimeout(() => {
+ promptInputs.style.display = "none";
+ promptInputYes.style.display = "none";
+ promptInputNo.style.display = "none";
+ promptInputCancel.style.display = "none";
+ promptInputOk.style.display = "none";
+ promptInputText.style.display = "none";
+ promptInputNumber.style.display = "none";
+ }, "500");
+}
+
+function getElements(){
+ promptBox = document.getElementById("prompt-container");
+ promptIcon = document.getElementById("prompt-icon");
+ promptTitle = document.getElementById("prompt-title");
+ promptText = document.getElementById("prompt-text");
+
+ promptInputText = document.getElementById("prompt-input-text");
+ promptInputNumber = document.getElementById("prompt-input-number");
+
+ promptInputs = document.getElementById("prompt-input-container");
+ promptInputYes = document.getElementById("prompt-button-yes");
+ promptInputNo = document.getElementById("prompt-button-no");
+ promptInputCancel = document.getElementById("prompt-button-cancel");
+ promptInputOk = document.getElementById("prompt-button-ok");
+}
+
+function setupPrompt(){
+ var code =
+ `
+
+
+
+
+
+
+
+
+
Oh yikes!
+
+ You've found a easter egg :0
+
+
+
+
+
+ Ok
+ Cancel
+ Yes
+ No
+
+
+
+
+ `;
+ document.body.insertAdjacentHTML("beforeend", code);
+
+ getElements();
+}
+
+var promptPromise;
+async function Confirm(title, text, icon, button, type) {
+ getElements();
+
+ promptBox.style.display = "block";
+ promptBox.style.animation = "fadein 0.5s";
+
+ promptTitle.innerHTML = title.replaceAll("#", " ");;
+ promptText.innerHTML = text.replaceAll("#", " ");
+ promptButtonClick = null;
+
+ var withText = false;
+ var withNumber = false;
+ var confirming = false;
+
+ if(type == null){
+ console.log("Couldnt show confirmation box because the type was null");
+ }
+
+ promptIcon.src = "/img/" + icon + ".png";
+ promptIcon.onerror = () => {
+ promptIcon.src = "/img/error.png";
+ }
+
+ if (Array.isArray(type) == true) {
+ type.forEach(input => {
+ if (input == "text") {
+ promptInputText.style.display = "block";
+ withNumber = true;
+ }
+ if (input == "number") {
+ withNumber = true;
+ promptInputNumber.style.display = "block";
+ }
+ if (input == "confirm") {
+ confirming = true;
+ }
+ });
+ } else {
+ if (type == "text") {
+ withText = true;
+ promptInputText.style.display = "block";
+ } else if (type == "number") {
+ withNumber = true;
+ promptInputNumber.style.display = "block";
+ }
+ else if (type == "confirm") {
+ confirming = true;
+ }
+ }
+
+ var executionCode = "";
+ if (Array.isArray(button) == true) {
+
+ var firstRun = true;
+ button.forEach(key => {
+
+ if(key[1] == null || key[1].length == 0){
+ key[1] = "closePrompt();";
+ }
+
+ if (key[0] == "yes") {
+ promptInputs.style.display = "block";
+ promptInputYes.style.display = "block";
+
+ promptInputYes.onclick = function(){ promptPromise("yes"); eval(key[1]) };
+
+ }
+ else if (key[0] == "no") {
+ promptInputs.style.display = "block";
+ promptInputNo.style.display = "block";
+ promptInputNo.onclick = function(){ promptPromise("no"); eval(key[1]) };
+ }
+ else if (key[0] == "cancel") {
+ promptInputs.style.display = "block";
+ promptInputCancel.style.display = "block";
+ promptInputCancel.onclick = function(){ promptPromise("cancel"); eval(key[1]) };
+ }
+ else if (key[0] == "ok") {
+ promptInputs.style.display = "block";
+ promptInputOk.style.display = "block";
+
+ promptInputOk.onclick = function(){ promptPromise("ok"); eval(key[1]) };
+ }
+ else {
+
+ if(firstRun == true){
+ promptInputs.innerHTML = "";
+ firstRun = false;
+ }
+
+ var token = "B" + generateId(8);
+ promptInputs.innerHTML += `${key[0]} `;
+ promptInputs.style.display = "block";
+
+ document.getElementById(token).onclick = function(){ promptPromise("ok"); eval(key[1]) };
+
+ /*
+ promptInputs.style.display = "block";
+ promptInputOk.style.display = "block";
+ promptInputOk.innerText = key[0];
+
+ promptInputOk.onclick = function(){ promptPromise("ok"); eval(key[1]) };
+
+ */
+ }
+ console.log(key);
+ });
+ }
+ else{
+ console.log("Button has to be 2 dimentional array")
+ return;
+ }
+
+ // Magic
+ // Waits for button press or until promptPromise() is called with value.
+ var promise = new Promise((resolve) => { promptPromise = resolve });
+ await promise.then((result) => { btnRes = result });
+
+ console.log("Button Result was " + btnRes)
+ closePrompt();
+
+ if(confirming == true){
+ if(btnRes == "yes"){
+ return true;
+ }
+ else if(btnRes == "no"){
+ return false;
+ }
+ else if(btnRes == "ok"){
+ return true;
+ }
+ else if(btnRes == "cancel"){
+ return null
+ }
+ }
+}
\ No newline at end of file
diff --git a/public/chat.js b/public/chat.js
index 7fde640..3c071e5 100644
--- a/public/chat.js
+++ b/public/chat.js
@@ -144,13 +144,13 @@ function markdown(msg, msgid){
} else if (isVideo(msg) == true) {
console.log("Is video")
- var code = `
+ var code = `
`;
//setTimeout(() => scrollDown(), 10)
- msg = msg.replace(url, `
+ msg = msg.replace(url, `
`)
@@ -216,89 +216,174 @@ async function checkConnection(delay) {
checkConnection(2000)
+// VC STUFF
+// Flag for recording or not
+var recordAudio = false;
+function stopAudioRecording(){
+ recordAudio = false;
+ socket.emit("leftVC", { id: getID() , username: getUsername(), icon: getPFP(), room: getRoom(), token: getToken() });
+}
-function mictest(){
- var constraints = { audio: true };
- navigator.mediaDevices.getUserMedia(constraints).then(function(mediaStream) {
- var mediaRecorder = new MediaRecorder(mediaStream);
+function joinVC(id){
- mediaRecorder.start();
+ document.getElementById("content").innerHTML = "";
+ getChannelTreeSocket();
+ socket.emit("getCurrentChannel", { id: getID() , username: getUsername(), icon: getPFP(), group: getGroup(), category: getCategory(), channel: getChannel(), token: getToken() });
+ socket.emit("joinedVC", { id: getID() , username: getUsername(), icon: getPFP(), room: getRoom(), token: getToken(), lastActivity: new Date().getTime() });
+ socket.emit("getVCMembers", { id: getID() , username: getUsername(), icon: getPFP(), room: getRoom(), token: getToken() }, function (response) {
- mediaRecorder.onstart = function(e) {
- //
- };
+ Object.keys(response.vcMembers).forEach(function(vcMember) {
+ addVCMember(response.vcMembers[vcMember])
+ })
- mediaRecorder.ondataavailable = async function(e) {
- var blob = new Blob([e.data], { 'type' : 'audio/ogg; codecs=opus' });
- socket.emit("sendVoiceData", {id:getID(), token: getToken(), voice: blob }, function (response) {
- // response
- });
- };
+ });
+ startAudioRecording();
+}
- mediaRecorder.onstop = function(e) {
- //
- };
+function startAudioRecording(){
- // Start recording
+ if(recordAudio == true){
+ return;
+ }
+ recordAudio = true;
+ navigator.mediaDevices.getUserMedia({ audio: true, video: false })
+ .then((stream) => {
+ var mediaRecorder = new MediaRecorder(stream);
+ mediaRecorder.audioBitsPerSecond = 700;
+ var audioChunks = [];
+ var minTime = 500;
- // Stop recording after 5 seconds and broadcast it to server
- setTimeout(function() {
- mediaRecorder.stop()
- }, 10);
- });
-}
+ mediaRecorder.start();
+ setTimeout(function () {
+ mediaRecorder.stop();
+ }, minTime);
+ mediaRecorder.addEventListener("dataavailable", function (event) {
+ audioChunks.push(event.data);
+ });
-async function getMedia(constraints) {
+ mediaRecorder.addEventListener("stop", function () {
- try {
- let stream = null;
+ if(recordAudio != false){
+ mediaRecorder.start();
+ setTimeout(function () {
+ mediaRecorder.stop();
+ }, minTime);
+ }
+ else{
+ stream.getTracks().forEach(function(track) {
+ track.stop();
+ });
+ }
+
+ var audioBlob = new Blob(audioChunks);
+ audioChunks = [];
+ var fileReader = new FileReader();
+ fileReader.readAsDataURL(audioBlob);
+ fileReader.onloadend = function () {
+ var base64String = fileReader.result;
+ socket.emit("audioStream", {id: getID(), token: getToken(), audioData: base64String, room: getRoom(), lastActivity: new Date().getTime()});
+ };
- stream = await navigator.mediaDevices.getUserMedia(constraints);
- var blob = new Blob([stream], { 'type' : 'audio/ogg; codecs=opus' });
- socket.emit("sendVoiceData", {id:getID(), token: getToken(), voice: blob }, function (response) {
- // response
+ });
+ })
+ .catch((error) => {
+ console.error('Error capturing audio.', error);
});
+}
- console.log(blob);
- let audio = new Audio();
- audio.srcObject = stream;
- audio.play();
+// When Receiving audio data
+socket.on('audioData', (data) => {
+ console.log(data)
+ console.log("Received data");
+ var newData = data.audioData.split(";");
+ newData[0] = "data:audio/ogg;";
+ newData = newData[0] + newData[1];
- } catch(err) {
- document.write(err)
- }
-}
+ var audio = new Audio(newData);
-//getMedia({ audio: true, video: false })
+ const audioContext = new AudioContext();
+ const mediaStreamAudioSourceNode = audioContext.createMediaElementSource(audio);
+ const analyserNode = audioContext.createAnalyser();
+ mediaStreamAudioSourceNode.connect(analyserNode);
-socket.on('receiveVoiceData', function (data) {
+ const pcmData = new Float32Array(analyserNode.fftSize);
+ analyserNode.getFloatTimeDomainData(pcmData);
+ let sumSquares = 0.0;
+ for (const amplitude of pcmData) { sumSquares += amplitude*amplitude; }
+ var finalDB = Math.sqrt(sumSquares / pcmData.length);
- console.log("RE")
+ console.log(finalDB);
- var blob = new Blob([data], { 'type' : 'audio/ogg; codecs=opus' });
- console.log(blob);
- var audio = document.createElement('audio'); // document.createElement('audio')
- audio.src = window.URL.createObjectURL(blob);
- audio.play();
- //data.play();
- /*
- let audio = new Audio();
- audio.srcObject = data;
+
+
+
+ mediaStreamAudioSourceNode.connect(audioContext.destination);
+
+ if (!audio || document.hidden) {
+ return;
+ }
audio.play();
+});
- */
+// When Receiving audio data
+socket.on('userJoinedVC', (member) => {
+ addVCMember(member);
});
+function addVCMember(member){
+ var userContentCheck = document.getElementById("vc-user-container-" + member.id);
+ if(userContentCheck != null) return;
+
+ var contentBox = document.getElementById("content")
+
+ var memberName = member.name;
+ if(memberName.length > 15){
+ memberName = member.name.substr(0, 15) + "...";
+ }
+
+ var userCode = `
+
+
+
+
${memberName}
+
`;
+
+ contentBox.insertAdjacentHTML("beforeend", userCode);
+}
+
+function removeVCUser(member){
+ var userContentCheck = document.getElementById(`vc-user-container-${member.id}`);
+ if(userContentCheck != null) userContentCheck.remove();
+}
+
+// When Receiving audio data
+socket.on('userLeftVC', (member) => {
+ removeVCUser(member)
+});
@@ -324,11 +409,16 @@ scope.addEventListener("click", (event) => {
clickedElement.className == "message-profile-info-name" ||
clickedElement.className == "memberlist-member-info name" ||
clickedElement.className == "memberlist-member-info status" ||
- clickedElement.className == "mention"
+ clickedElement.className == "mention" ||
+ clickedElement.id.includes("vc-user-container") ||
+ clickedElement.id.includes("vc-user-icon") ||
+ clickedElement.id.includes("vc-user-name")
){
var userid = clickedElement.id;
- if(clickedElement.className == "mention") { userid = userid.replace("mention-", "")}
+ //if(clickedElement.className == "mention") { userid = userid.replace("mention-", "")}
+ userid = userid.split("-").pop();
+ console.log("Userid is " + userid)
getMemberProfile(userid, mouseX, mouseY);
}
else if(clickedElement.className.includes("role") && clickedElement.id.split("-")[0] == "addRole"){
@@ -566,9 +656,15 @@ scope.addEventListener("contextmenu", (event) => {
socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "manageChannels" }, function (response) {
if(response.permission == "denied") { return; }
- addContextMenuItem(ContextMenu, "Create Channel",
+ addContextMenuItem(ContextMenu, "Create Text Channel",
`onclick="
- createChannel('${clickedElement.id}');
+ createChannel('${clickedElement.id}', 'text');
+ ContextMenu.classList.remove('visible');
+ "`);
+
+ addContextMenuItem(ContextMenu, "Create Voice Channel",
+ `onclick="
+ createChannel('${clickedElement.id}', 'voice');
ContextMenu.classList.remove('visible');
"`);
});
@@ -597,9 +693,15 @@ scope.addEventListener("contextmenu", (event) => {
socket.emit("checkPermission", {id:getID(), token: getToken(), permission: "manageChannels" }, function (response) {
if(response.permission == "denied") { return; }
- addContextMenuItem(ContextMenu, "Create Channel",
+ addContextMenuItem(ContextMenu, "Create Text Channel",
+ `onclick="
+ createChannel('${clickedElement.id}', 'text');
+ ContextMenu.classList.remove('visible');
+ "`);
+
+ addContextMenuItem(ContextMenu, "Create Voice Channel",
`onclick="
- createChannel('${clickedElement.id}');
+ createChannel('${clickedElement.id}', 'voice');
ContextMenu.classList.remove('visible');
"`);
});
@@ -718,12 +820,10 @@ scope.addEventListener("contextmenu", (event) => {
if((ContextMenu.offsetHeight*4) + mouseY > document.body.offsetHeight){
ContextMenu.style.top = `${mouseY - ContextMenu.offsetHeight}px`;
ContextMenu.style.left = `${mouseX}px`;
- console.log("is out of bounds")
}
else{
ContextMenu.style.top = `${mouseY}px`;
ContextMenu.style.left = `${mouseX}px`;
- console.log("is not out of bounds")
}
@@ -815,7 +915,6 @@ function createCategory(){
var catname = prompt("Category Name:");
if(catname == null ||catname.length <= 0){
- console.log("No name?")
return;
}
else{
@@ -824,19 +923,19 @@ function createCategory(){
}
-function createChannel(category){
+function createChannel(category, channelType){
var catname = prompt("Channel Name:");
if(catname == null ||catname.length <= 0){
return;
}
else{
- socket.emit("createChannel", { id: getID(), value: catname, token: getToken(), group: getGroup().replace("group-", ""), category: category.replace("category-", "")});
+ socket.emit("createChannel", { id: getID(), value: catname, type: channelType, token: getToken(), group: getGroup().replace("group-", ""), category: category.replace("category-", "")});
+
}
}
function deleteChannel(id){
- console.log(id);
socket.emit("deleteChannel", { id: getID(), token: getToken(), channelId: id, group: getGroup().replace("group-", "")});
}
@@ -947,7 +1046,7 @@ function userJoined(){
*/
}
else{
- console.log("gay")
+
}
}
@@ -1011,8 +1110,6 @@ function changePFP(){
if(pfp.length > 0){
setCookie("pfp", pfp, 360);
updatePFPOnUI(pfp, true);
-
- console.log("Letting Server know pfp changed");
}
else{
@@ -1096,20 +1193,6 @@ function isImage(url){
const img = new Image();
- /*
- if(notAImage.includes(url)){
- console.log("Not a Image")
- return false;
- }
-
- if(validImage.includes(url)){
- return true;
- }
-
- */
-
- //console.log("checking link " + url)
-
img.src = url;
@@ -1347,24 +1430,12 @@ var test = 0;
var testrun = 0;
function sendMessage(messagebox) {
- //console.log(event.keyCode)
-
-
if(event.keyCode != 13){
lastKey = event.keyCode;
}
- /*
- if(event.keyCode == 8){
-
- }
- */
-
// Adding new line
if(event.keyCode == 13 && lastKey == 16 && testrun < 6){
- //document.getElementById("messagebox").style.height = `calc(${document.getElementById("messagebox").offsetHeight}px + 5px) !important;`
-
- /*document.getElementById("messagebox").offsetHeight +*/
if(test == 0){
test = 44;
@@ -1494,8 +1565,6 @@ function convertMention(text, playSoundOnMention = false){
if(playSoundOnMention == true)
{
- //console.log("PLayed message sound");
- //console.log(playSoundOnMention)
playSound("message", 0.5);
}
}
@@ -1557,8 +1626,6 @@ socket.on('messageCreate', function (message) {
var diff = today - lastMessage;
var minutesPassed = Math.round(diff / 60);
- //console.log("Past: " + minutesPassed + " minutes");
-
if(authorDivs[0].id == message.id && minutesPassed < 5){
messagecontent[0].insertAdjacentHTML("beforeend",
`${message.message.replaceAll("\n", " ")}
`
@@ -1655,9 +1722,6 @@ function deleteMessageFromChat(id){
}
function bulkDeleteMessageFromChat(id){
-
-
- //var children = [].slice.call(document.getElementById(id));
var children = null;
try{
@@ -1669,14 +1733,10 @@ function bulkDeleteMessageFromChat(id){
children = document.querySelector(`#${id}`).parentNode;
}
- //console.log("Child")
- //console.log(children)
children = children.querySelector("p");
console.log(children)
for (var i = 0; i < children.length; i++) {
- //console.log(children[i]); //second console output
-
socket.emit("deleteMessage", { id: getID(), token: getToken(), messageId: children[i].id.replace("msg-", ""),
group: getGroup().replace("group-", ""), category: getCategory().replace("category-", ""), channel: getChannel().replace("channel-", "") });
@@ -1687,32 +1747,14 @@ socket.on('receiveDeleteMessage', function (id) {
console.clear();
- //var parent = document.querySelector(`#msg-${CSS.escape(id)}`);
- //parent.remove();
- //var container = document.querySelector(`.message-container #${id}`).parentNode.parentNode;
- //console.log(container)
-
- console.log(`Deleting from chat #msg-${id}`)
- console.log(`Scanning for #msg-${id}`)
- //var parent = document.querySelector(`#msg-${id} p`).parentNode.parentNode;
-
-
- // document.querySelector(`#msg-152598637369 p`).parentNode;
var message = document.querySelectorAll(`div .message-profile-content #msg-${id}`);
var parentContainer = message[0].parentNode.parentNode;
var parent = message[0].parentNode;
-
- console.log("Message is:")
- console.log(message)
message.forEach(msg => {
msg.remove();
});
- console.log("parent: ")
- console.log(parent)
- console.log(parent.children.length)
-
if(parentContainer.querySelector(".message-profile-content-message") == null){
parentContainer.remove();
}
@@ -1768,8 +1810,6 @@ socket.on('receiveChannelTree', function (data) {
var markedMessage3 = [];
markedMessage3 = getCookie("unmarkedMessages");
-
- console.log(markedMessage3);
}
catch(Ex){
//console.log(Ex)
@@ -1880,26 +1920,15 @@ socket.on('receiveMemberProfile', function (data) {
// If is out of bounds
- /*
- console.log(winHeight)
- console.log(data.top);
- console.log(profileContent.offsetHeight);
- console.log((profileContent.offsetHeight - data.top));
-
- */
-
if((data.top + profileContent.offsetHeight) <= winHeight){
profileContent.style.top = `${data.top}px`;
- //console.log("first");
}
else{
if(data.top + profileContent.offsetHeight > winHeight){
profileContent.style.top = `${data.top - ((data.top + profileContent.offsetHeight) - winHeight) - 20}px`;
- //console.log("second");
}
else{
profileContent.style.top = `${data.top - (winHeight - profileContent.offsetHeight)}px`;
- //console.log("second");
}
}
@@ -1997,8 +2026,6 @@ socket.on('receiveToken', function (data) {
socket.on('modalMessage', function (data) {
- console.log(data);
-
var buttonArray = [];
Object.keys(data.buttons).forEach(function(button) {
@@ -2008,12 +2035,6 @@ socket.on('modalMessage', function (data) {
buttonArray.push([buttonText.toLowerCase(), buttonEvents])
});
- for(let i = 0; i < data.buttons.length; i++){
- console.log("button : " + data.buttons[i])
- }
-
- console.log(buttonArray);
-
Confirm(data.title, data.message, "info", buttonArray, "confirm").then(result => {
console.log(result);
@@ -2029,7 +2050,6 @@ function setActiveGroup(group){
function addRoleFromProfile(userId){
socket.emit("getAllRoles", {id:getID(), token: getToken(), group: getGroup(), targetUser: userId }, function (response) {
- console.log(response)
var roleList = document.getElementById("profile-role-menu").querySelector("#role-menu-list");
roleList.innerHTML = "";
@@ -2039,7 +2059,6 @@ function addRoleFromProfile(userId){
var roleObj = roles[role]
- console.log(roleObj)
var roleId = roleObj.info.id;
var roleName = roleObj.info.name;
var roleColor = roleObj.info.color;
@@ -2172,12 +2191,6 @@ function resetAccount(){
document.getElementById("message-actions").onclick = function(e) {
- // e = Mouse click event.
- //var rect = e.target.getBoundingClientRect();
- //var x = e.clientX - rect.left; //x position within the element.
- //var y = e.clientY - rect.top; //y position within the element.
- //console.log("Left? : " + x + " ; Top? : " + y + ".");
-
var x = e.clientX;
var y = e.clientY;
@@ -2199,16 +2212,6 @@ document.getElementById("message-actions").onclick = function(e) {
var test = document.getElementById("message-actions-image");
-
-
- /*
- console.log(emojiBox.offsetHeight)
- emojiBox.style.top = ((test.style.top + (emojiBox.offsetHeight * 2)) - 60) + "px";
- emojiBox.style.left = ((test.style.left + emojiBox.offsetWidth * 3.1) + "px");
-
- */
-
-
emojiBox.style.top = (y - emojiBox.offsetHeight - 40) + "px";
emojiBox.style.left = x - emojiBox.offsetWidth +"px";
}
@@ -2476,14 +2479,28 @@ function getServerInfo(returnData = false){
});
}
-function setUrl(param){
+function setUrl(param, isVC = false){
window.history.replaceState(null, null, param); // or pushState
- chatlog.innerHTML = "";
- document.getElementById("messagebox-content").focus();
+ if(isVC == true){
+ socket.emit("setRoom", { id: getID() , username: getUsername(), icon: getPFP(), room: getRoom(), token: getToken() });
+
+ joinVC(param);
+ document.getElementById("messagebox").style.visibility = "hidden";
+ document.getElementById("content").innerHTML = "";
+ return;
+ }
+ else{
+ if(recordAudio ) stopAudioRecording();
+ chatlog.innerHTML = "";
+ document.getElementById("messagebox").style.visibility = "visible";
+ document.getElementById("messagebox-content").focus();
+ }
+ socket.emit("setRoom", { id: getID() , username: getUsername(), icon: getPFP(), room: getRoom(), token: getToken() });
refreshValues();
+
}
function setChannelName(name){
@@ -2523,10 +2540,8 @@ function upload(files) {
socket.emit("fileUpload", {file: files, filename: files.name, id:getID(), token: getToken() }, function (response) {
if(response.type == "success"){
- //notify(response.msg, "success")
console.log(response);
- //console.log(`sending ${window.location.origin + response.msg}`)
sendMessageToServer(getID(), getUsername(), getPFP(), window.location.origin + response.msg);
}
else{
diff --git a/public/settings/server/page/whats-new/whats-new.html b/public/settings/server/page/whats-new/whats-new.html
index a9b8581..af4a227 100644
--- a/public/settings/server/page/whats-new/whats-new.html
+++ b/public/settings/server/page/whats-new/whats-new.html
@@ -32,16 +32,108 @@ What's new?
-
Bug Fix April 21st, 2024 | v6.4.5
+ Bug Fix April 21st, 2024 | v2.6.6
Styling Bugs
- Fixed a bug where the server group list would be centered vertically.
+ Fixed a bug where the server group list would be centered vertically for some reason
+
+
+
+
+ Other Bugs
+
+
+ Fixed a bug where online members are shown as offline
+
+
+ Fixed a bug where online members are shown as offline
+
+
+ (hopfully for good!) Fixed a bug where video embeds show as error
+
+
+ (hopfully for good!) Fixed a bug where video embeds show as error
+
+
+ Fixed Status text overlapping borders
+
+
+ Fixed a bug where sometimes video embeds have white borders
+
+
+ Fixed a bug where editing the channel name wouldnt save the new name
+
+
+ Added black background color to video embeds (mobile videos etc)
+
+
+ Fixed the member list showing members that dont have access to the channel.
+
+
+ Fixed a bug where you could demote / promote members to the same role as yourself (Admins were able to give users Admin or remove other Admins)
+
+
+ Fixed a bug where editing a hidden group or channel would make that channel visible for users (tho not the channel content)
+
+
+ Fixed a bug where updating the server banner in a hidden group would change the banner for everyone
+
+
+ Fixed some other network related event bugs
+
+
+
+
+
+
+
+
New Features
+
+
+ Voice Chat
+
+
+ Added a experimental voice chat feature
+
+
+
+ You can now create text and voice channels in the channel tree using the right click context menu
+
+
+
+ Timeout / Mute
+
+
+ Its now possible to mute people for an infinite amount of time or specified amount of seconds/minutes
+
+
+
+ Custom Kick / Ban Messages
+
+
+ Its now possible to add a ban and kick reason when doing so.
+
+
+
+
+
+
Open Source Release
+
+
+ Not Obfuscated anymore!
+
+
+ The code is no longer obfuscated and can be seen on Github.
+
+
+
+
@@ -57,7 +149,7 @@ Bug Fix April 21st, 2024 | v6.4.5