// ==UserScript==
// @name ServerSelector
// @namespace http://tampermonkey.net/
// @version 1.1.2
// @description Select servers from different gamemodes and regions.
// @author Altanis + Bismuth
// @match *://diep.io/*
// @icon data:image/gif;base64,R0lGODlhAQABAAAAACH5BAEKAAEALAAAAAABAAEAAAICTAEAOw==
// @grant unsafeWindow
// @license MIT
// ==/UserScript==
// Special credits to Diep7444 for paving the way to an effective region changer.
const textShadow = 'text-shadow:black 0.18vh 0, black -0.18vh 0, black 0 -0.18vh, black 0 0.18vh, black 0.18vh 0.18vh, black -0.18vh 0.18vh, black 0.18vh -0.18vh, black -0.18vh -0.18vh, black 0.09vh 0.18vh, black -0.09vh 0.18vh, black 0.09vh -0.18vh, black -0.09vh -0.18vh, black 0.18vh 0.09vh, black -0.18vh 0.09vh, black 0.18vh -0.09vh, black -0.18vh -0.09vh'
const regions = ["do-sfo","do-nyc","do-fra","do-sgp"];
const modes = ["ffa", "teams", "4teams", "maze"];
const colors = ["#00b2e1","#bf7ff5","#00e16e","#f14e54","#FDD023"];
const modeHTML = document.createElement("div");
document.body.appendChild(modeHTML);
modeHTML.innerHTML = `
<div class='parent' id='mode' style='user-select:none; position:fixed; bottom:43%; right:0.5%; text-align:center; width:20vw; font-family:Ubuntu; color:#FFFFFF; font-style:normal; font-size:0.9vw; ${textShadow}'> <div class='child' style='line-height:2vh; opacity:75%'>
If no servers are showing, be patient.
TAB to hide menu.
WARNING! Do not repeatedly press buttons, as you may be ratelimited and will be unable to access diep for 15 minutes.
<br>
<p style="font-size:12px">Created by Altanis and Bismuth</p>
<p style="font-size:12px">Credits to Diep7444</p>
<hr>
</div>
<button class='child' type='button' id='ffa' value='mode' style='width:3.5vw; height:3vh; font-family:Ubuntu; opacity:75%; background:${colors[0]}; color:#FFFFFF; font-style:normal; font-size:0.9vw; ${textShadow}'>FFA</button>
<button class='child' type='button' id='teams' value='mode' style='width:3.5vw; height:3vh; font-family:Ubuntu; opacity:75%; background:${colors[1]}; color:#FFFFFF; font-style:normal; font-size:0.9vw; ${textShadow}'>2TDM</button>
<button class='child' type='button' id='4teams' value='mode' style='width:3.5vw; height:3vh; font-family:Ubuntu; opacity:75%; background:${colors[2]}; color:#FFFFFF; font-style:normal; font-size:0.9vw; ${textShadow}'>4TDM</button>
<button class='child' type='button' id='maze' value='mode' style='width:3.5vw; height:3vh; font-family:Ubuntu; opacity:75%; background:${colors[3]}; color:#FFFFFF; font-style:normal; font-size:0.9vw;${textShadow}'>MAZE</button>
<button class='child' type='button' id='sandbox' value='mode' style='width:3.5vw; height:3vh; font-family:Ubuntu; opacity:75%; background:${colors[4]}; color:#FFFFFF; font-style:normal; font-size:0.9vw;${textShadow}'>SBX</button>
<button class='child' type='button' id='do-sfo' value='region' style='width:3.5vw; height:3vh; font-family:Ubuntu; opacity:75%; background:${colors[0]}; color:#FFFFFF; font-style:normal; font-size:0.9vw; ${textShadow}'>SFO</button>
<button class='child' type='button' id='do-nyc' value='region' style='width:3.5vw; height:3vh; font-family:Ubuntu; opacity:75%; background:${colors[1]}; color:#FFFFFF; font-style:normal; font-size:0.9vw; ${textShadow}'>NYC</button>
<button class='child' type='button' id='do-fra' value='region' style='width:3.5vw; height:3vh; font-family:Ubuntu; opacity:75%; background:${colors[2]}; color:#FFFFFF; font-style:normal; font-size:0.9vw; ${textShadow}'>FRA</button>
<button class='child' type='button' id='do-sgp' value='region' style='width:3.5vw; height:3vh; font-family:Ubuntu; opacity:75%; background:${colors[3]}; color:#FFFFFF; font-style:normal; font-size:0.9vw;${textShadow}'>SGP</button>
<div class='parent' id='choice' style='user-select:none; position:fixed; bottom:34%; right:0.5%; text-align:center; width:15vw; font-family:Ubuntu; color:#FFFFFF; font-style:normal; font-size:0.9vw; ${textShadow}'>
</div>
</div>
`
document.getElementById('mode').style.display = 'block';
addButtonListener('ffa');
addButtonListener('teams');
addButtonListener('4teams');
addButtonListener('maze');
addButtonListener('sandbox');
addButtonListener('do-sfo');
addButtonListener('do-nyc');
addButtonListener('do-fra');
addButtonListener('do-sgp');
function refreshHTML() {
let json = "<div class='parent' id='choice' style='user-select:none; position:fixed; bottom:37%; right:0.5%; text-align:center; width:15vw; font-family:Ubuntu; color:#FFFFFF; font-style:normal; font-size:0.9vw; ${textShadow}'>" + choices.mode + " - " + choices.region + " <hr></div>";
for (let n = 0; n < serverWithoutCSS[choices.mode][choices.region].length; n++) {
json += "<button class='child' type='button' id='choice" + n + "' value='"+ n + "' style='width:5vw; height:3vh; font-family:Ubuntu; opacity:75%; background:" + colors[n % 7] + "; color:#FFFFFF; font-style:normal; font-size:0.9vw;" + textShadow + "}'>" + serverWithoutCSS[choices.mode][choices.region][n].slice(0,8) + "</button>";
}
json += "</div>"
document.getElementById('choice').innerHTML = `${json}`;
for (let n = 0; n < serverWithoutCSS[choices.mode][choices.region].length; n++) {
addButtonListener('choice'+n);
}
}
function buttonAction(id) {
let button = document.getElementById(id);
if (button.value === 'mode') {
choices.mode = id;
fetchServer(choices.mode, choices.region, 3);
}
else if (button.value === 'region') {
choices.region = id;
fetchServer(choices.mode, choices.region, 3);
}
else {
(connectTo(choices.mode, choices.region, button.value));
}
refreshHTML();
}
function addButtonListener(id) {
document.getElementById(id).addEventListener("click", function() {buttonAction(id)});
document.getElementById(id).addEventListener("mouseenter", function() {lightenColor(id)});
document.getElementById(id).addEventListener("mouseleave", function() {resetColor(id)});
}
function lightenColor(id) {
document.getElementById(id).style.opacity = '100%'
}
function resetColor(id) {
document.getElementById(id).style.opacity = '75%'
}
const choices = {
mode: 'ffa',
region: 'do-sfo'
}
const serverWithoutCSS = {
"ffa": {
"do-sfo": [],
"do-nyc": [],
"do-fra": [],
"do-sgp": []
},
"teams": {
"do-sfo": [],
"do-nyc": [],
"do-fra": [],
"do-sgp": []
},
"4teams": {
"do-sfo": [],
"do-nyc": [],
"do-fra": [],
"do-sgp": []
},
"maze": {
"do-sfo": [],
"do-nyc": [],
"do-fra": [],
"do-sgp": []
},
"sandbox": {
"do-sfo": [],
"do-nyc": [],
"do-fra": [],
"do-sgp": []
},
};
const servers = [];
var do_connect = false;
var currentServer = '';
async function fetchServer(mode, region, times, ids = []) {
if (mode === 'sandbox') times = 1;
const url = "https://api-game.rivet.gg";
for (let i = 0; i < times; i++) {
try {
const response = await fetch(`${url}/v1/matchmaker/lobbies/find`, {method: 'post', body: `{"game_modes": ["${mode}"], "regions": ["${region}"]}`});
const body = await response.json();
if (body.hasOwnProperty("lobby")) {
Object.entries(body.lobby.ports).forEach(([key, val]) => {
if (!serverWithoutCSS[mode][region].some((host) => {
return host === val.host;
})) {
serverWithoutCSS[mode][region].push(val.host);
servers.push(mode + " " + region + " " + serverWithoutCSS[mode][region].length + ": " + val.host.slice(0,8));
const txt = key;
}
});
}
} catch (err) {
console.error(err);
}
}
refreshHTML();
}
function appendServers(mode, region) {
fetchServer(mode, region, 3);
}
function connectTo(mode, region, number) {
if (!serverWithoutCSS[mode][region][number]) return;
currentServer = "wss://" + serverWithoutCSS[mode][region][number];
do_connect = true;
unsafeWindow.input.execute('lb_reconnect');
}
unsafeWindow.servers = serverWithoutCSS;
unsafeWindow.WebSocket = new Proxy(WebSocket, {construct(t, args) {
if (do_connect) args[0] = currentServer;
do_connect = false; return Reflect.construct(t, args)}});
document.body.onkeydown = function(e) {
if (e.keyCode === 9) {
if (document.getElementById('mode').style.display === "none") {
document.getElementById('mode').style.display = "block";
document.getElementById('choice').style.display = "block";
} else {
document.getElementById('mode').style.display = "none";
document.getElementById('choice').style.display = "none";
}
}
}