Neon's custom editor

A Mod to extend editor functionality.

目前为 2024-05-04 提交的版本。查看 最新版本

// ==UserScript==
// @name         Neon's custom editor
// @namespace    http://tampermonkey.net/
// @version      v1.0.1
// @description  A Mod to extend editor functionality.
// @author       iNeonz
// @match        https://heav.io/game.html
// @match        https://hitbox.io/game.html
// @match        https://heav.io/game2.html
// @match        https://hitbox.io/game2.html
// @match        https://hitbox.io/game-beta.html
// @require      https://unpkg.com/blockly/blockly.min.js
// @icon         https://www.google.com/s2/favicons?sz=64&domain=heav.io
// @grant        none
// @run-at       document-idle
// ==/UserScript==

const version = "v1.0.1";
const codeNames = {};
let jsSwitch = false;
const codeNamesRegex = {
    "simulation": {
        reg: /\];\}.{0,2}\(.{0,3}\) {var .{0,3},.{0,3},.{0,3},.{0,3},.{0,3},.{0,3};(.*?)\{throw new Error\("Failed to simulate(.*?)\);\}(.*?)\.step\((.*?)\);(.*?).{0,2}\(\);(.*?)\}.{0,2}\(\)/ig,
        verify: function(match)
        {
            //console.log(match);
            let world = match[0].match(/this\..{2,2}\.step\(/ig)[0];
            let sim = match[0].split(";}")[1].split("(")[0];
            //console.log(sim);
            let thisses = match[0].split("this.");
            //console.log(thisses);
            for (let i of thisses){
                if (i.match("=")){
                    i = i.split("=")[0];
                }else{
                    i = null;
                }
            }
            thisses.filter(a => a != null);
            return [sim,thisses[1].split(".")[0],thisses[1].split(".")[1].split("(")[0],world.split("this.")[1].split(".")[0]];
        }
    },
}

function appendScript(link,head){
    let scr = document.createElement("script");
    scr.src = link;
    (head? document.head : document.body).appendChild(scr);
}


fetch(`https://hitbox.io/bundle.js`)
    .then(code => code.text())
    .then(code => {
    parent.document.getElementById("adboxverticalright").style.right = "100000%";
    parent.document.getElementById("adboxverticalleft").style.left = "-200%";
    for (let i in codeNamesRegex){
        codeNames[i] = codeNamesRegex[i].verify(code.match(codeNamesRegex[i].reg));
    }

    const newScope = (scope, script) => Function(`"use strict"; const globalThis = null; const window = null; const document = null; const game = this; for (let i in game.usedMath) {Math[i] = (...args) => {return game.Math[i](...args)};}; ${script}`).bind(scope);
    let DN = [
        "gsFightersCollide",
        "recordMode",
        "o",
        "l",
        "u",
        "m",
        "g",
        "v",
        "k",
        "N",
        "S",
        "M",
        "C",
        "_",
        "T",
        "P",
        "B",
        "I",
        "F",
        "R",
        "O",
        "A",
        "D",
        "L",
        "U",
        "H",
        "J",
        "W",
        "G",
        "Y", // ss
        "V",
        "q",
        "K",
        "X",
        "Z",
        "$",
        "tt",
        "it",
        "st",
        "ht",
        "et",
        "nt",
        "ot",
        "rt",
        "at",
        "lt",
        "ut",
        "ct",
        "dt",
        "wt",
        "ft",
        "gt",
        "bt"
    ]


    let stateMaker;
    let mostScore = -1;

    for (let a1 in window.multiplayerSession){
        let a = window.multiplayerSession[a1];
        if (typeof a == "object")
        {
            let score = 0;
            for (let x1 in a){
                let x = a[x1];
                if (typeof x == "object")
                {
                    if (x.constructor.name == "Array"){

                    }
                    else
                    {
                        let length = 0;
                        for (let y1 in x){
                            let y = x[y1];
                            length++
                            if (length > 2){
                                break;
                            }
                        }
                        if (length == 1){
                            for (let y1 in x){
                                let y = x[y1];
                                if (y.constructor.name == "Map"){
                                    score++
                                }
                                break;
                            }
                        }else{
                            let isDN = true;
                            for (let i of DN){
                                if (!i in x){
                                    isDN = false;
                                    break;
                                }
                            }
                            if (isDN){
                                score+=5;
                            }
                        }
                    }
                }
            }
            if (score > mostScore && score < 50){
                mostScore = score;
                stateMaker = a;
            }
        }
    }
    function encodeState(state){
        let newState = state;
        newState.cubes = newState.all[8];
        newState.projectiles = [];
        for (let id in newState.all[9]){
            let proj = newState.all[9][id];
            if (proj && codeNames.general){
                if (!codeNames.projectiles){
                    let matches = String(proj.constructor).match(/this\.(.*?)=(.*?);/ig);
                    let m = [];
                    for (let i of matches){
                        m.push(i.split("this.")[1].split("=")[0]);
                    }
                    codeNames.projectiles = m;
                }
                let newProj = {
                    p: [proj.x,proj.y],
                    lv: [proj[codeNames.lv[0]],proj[codeNames.lv[1]]],
                    a: proj.angle,
                    av: proj.angularVelocity,
                    ftd: proj[codeNames.projectiles[10]],
                    tr: proj[codeNames.projectiles[14]], // turn rate
                    gs: proj[codeNames.projectiles[17]], // gravity scale
                    er: proj[codeNames.projectiles[15]], // explode radius
                    bb: proj[codeNames.projectiles[18]], // bullet bounces
                    owner: proj[codeNames.projectiles[13]],
                    round: proj[codeNames.projectiles[24]], // bullet round
                    restitution: proj.restitution, // bullet restitution
                    bc: proj[codeNames.projectiles[22]], // bounce count
                    br: proj[codeNames.projectiles[6]], // bullet radius
                }
                newState.projectiles[id] = newProj;
            }
        }
        for (let id in newState.all[13]){
            if (codeNames.general && newState.all[13][id]){
                let flag = newState.all[13][id];
                if (!codeNames.flags){
                    let constructor = String(flag.constructor);
                    let matches = constructor.match(/this\..{0,2}=(.*?);/ig);
                    let m = [];
                    for (let i of matches){
                        m.push(i.split("this.")[1].split("=")[0]);
                    }
                    let t = [''];
                    for (let i in m) {
                        t.push(m[i]);
                    }
                    codeNames.flags = t;
                }
                flag.p = [flag.x,flag.y];
                flag.capFrames = flag[codeNames.flags[7]];
                flag.capLimit = flag[codeNames.flags[6]];
                flag.takenBy = flag[codeNames.flags[5]];
            }
        }
        newState.flags = newState.all[13];
        for (let id in newState.cubes){
            let cube = newState.cubes[id];
            if (!codeNames.general){
                let constructor = String(cube.constructor);
                let matches = constructor.match(/this\..{0,2}=(.*?);/ig);
                let m = [];
                for (let i of matches){
                    m.push(i.split("this.")[1].split("=")[0]);
                }
                let t = [''];
                for (let i in m) {
                    t.push(m[i]);
                }
                codeNames.general = t;
                codeNames.lv = [codeNames.general[4],codeNames.general[5]]
            }
            cube.p = [cube.x,cube.y];
            cube.lv = [cube[codeNames.lv[0]],cube[codeNames.lv[1]]];
            cube.st = cube[codeNames.general[21]];
            cube.team = cube[codeNames.general[9]];
            cube.ff = cube[codeNames.general[15]];
            cube.dj = cube[codeNames.general[10]];
            cube.rf = cube[codeNames.general[30]];
            cube.hp = cube[codeNames.general[8]];
            cube.ra = cube[codeNames.general[31]];
            cube.stepsSurvived = cube[codeNames.general[14]];
            cube.iframes = Math.max(0,cube[codeNames.general[13]]-1);
            cube.ba = cube[codeNames.general[25]];
            cube.bf = cube[codeNames.general[24]];
            cube.a = cube.angle;
            cube.av = cube.angularVelocity;
            delete cube.angle;
            delete cube.angularVelocity;
            delete cube[codeNames.general[21]];
            delete cube[codeNames.general[8]];
            delete cube[codeNames.general[14]];
            delete cube[codeNames.general[22]];
            delete cube[codeNames.lv[0]];
            delete cube[codeNames.lv[1]];
            delete cube.x;
            delete cube.y;
        }
        for (let id in newState.all[4]){
            let info = newState.all[4][id];
            if (!codeNames.deathReg){
                let constructor = String(info.constructor);
                let matches = constructor.match(/this\..{0,2}=(.*?);/ig);
                let m = [];
                for (let i of matches){
                    m.push(i.split("this.")[1].split("=")[0]);
                }
                let t = [];
                for (let i in m) {
                    t.push(m[i]);
                }
                codeNames.deathReg = t;
            }
            let playerData = info[codeNames.deathReg[10]];
            let finalPlrData = {};
            for (let id2 in playerData){
                let info2 = playerData[id2];
                if (info2){
                    if (!codeNames.playerReg){
                        let constructor = String(info2.constructor);
                        let matches = constructor.match(/this\..{0,2}=(.*?);/ig);
                        let m = [];
                        for (let i of matches){
                            m.push(i.split("this.")[1].split("=")[0]);
                        }
                        let t = [];
                        for (let i in m) {
                            t.push(m[i]);
                        }
                        codeNames.playerReg = t;
                    }
                    info2.lives = info2[codeNames.playerReg[14]];
                    info2.kills = info2[codeNames.playerReg[2]];
                    info2.respawnIndex = info2[codeNames.playerReg[34]];
                    info2.killedBy = info2[codeNames.playerReg[18]];
                    info2.respawn = info2[codeNames.playerReg[12]];
                }
            }
            newState.playerData = playerData;
        }
        return newState;
    }

    let lastPixiContainer = null;

    function decodeState(state) {
        let newState = state;
        newState.all[8] = newState.cubes;
        for (let id in newState.projectiles){
            let proj = newState.projectiles[id];
            let p = newState.all[9][id];
            if (proj && p && codeNames.general){
                p.x = proj.p[0]
                p.y = proj.p[1]
                p[codeNames.lv[0]] = proj.lv[0]
                p[codeNames.lv[1]] = proj.lv[1]
                p.angle = proj.a;
                p.angularVelocity = proj.av;
                p[codeNames.projectiles[10]] = proj.ftd;
                p[codeNames.projectiles[14]] = proj.tr; // turn rate
                p[codeNames.projectiles[17]] = proj.gs; // gravity scale
                p[codeNames.projectiles[15]] = proj.er; // explode radius
                p[codeNames.projectiles[18]] = proj.bb; // bullet bounces
                p[codeNames.projectiles[13]] = proj.owner;
                p[codeNames.projectiles[24]] = proj.round; // bullet round
                p.restitution = proj.restitution; // bullet restitution
                p[codeNames.projectiles[22]] = proj.bc; // bounce count
                p[codeNames.projectiles[6]] = proj.br; // bullet radius
            }
        }
        delete newState.projectiles;
        newState.all[13] = newState.flags;
        for (let id in newState.all[13]){
            if (codeNames.general && newState.all[13][id]){
                let flag = newState.all[13][id];
                if (!codeNames.flags){
                    let constructor = String(flag.constructor);
                    let matches = constructor.match(/this\..{0,2}=(.*?);/ig);
                    let m = [];
                    for (let i of matches){
                        m.push(i.split("this.")[1].split("=")[0]);
                    }
                    let t = [''];
                    for (let i in m) {
                        t.push(m[i]);
                    }
                    codeNames.flags = t;
                }
                if (flag.p){
                    flag.x = flag.p[0];
                    flag.y = flag.p[1];
                    flag[codeNames.flags[7]] = flag.capFrames;
                    flag[codeNames.flags[6]] = flag.capLimit;
                    flag[codeNames.flags[5]] = flag.takenBy;
                }
            }
        }
        for (let id in newState.all[8]){
            let cube = newState.all[8][id];
            if (!codeNames.general){
                let constructor = String(cube.constructor);
                let matches = constructor.match(/this\..{0,2}=(.*?);/ig);
                let m = [];
                for (let i of matches){
                    m.push(i.split("this.")[1].split("=")[0]);
                }
                let t = [''];
                for (let i in m) {
                    t.push(m[i]);
                }
                codeNames.general = t;
                codeNames.lv = [codeNames.general[4],codeNames.general[5]]
            }
            cube.x = cube.p[0];
            cube.y = cube.p[1];
            cube[codeNames.lv[0]] = cube.lv[0];
            cube[codeNames.lv[1]] = cube.lv[1];
            cube.angularVelocity = cube.av;
            cube[codeNames.general[10]] = cube.dj;
            cube[codeNames.general[8]] = cube.hp;
            cube[codeNames.general[13]] = cube.iframes;
            cube[codeNames.general[21]] = cube.st;
            cube[codeNames.general[15]] = cube.ff;
            cube[codeNames.general[9]] = cube.team;
            cube[codeNames.general[30]] = cube.rf;
            cube[codeNames.general[31]] = cube.ra;
            cube[codeNames.general[14]] = cube.stepsSurvived;
            cube[codeNames.general[25]] = cube.ba;
            cube[codeNames.general[24]] = cube.bf;
            cube.angle = cube.a;
            delete cube.a;
            delete cube.av;
            delete cube.stepsSurvived;
            delete cube.st;
            delete cube.dj;
            delete cube.iframes;
            delete cube.lv;
            delete cube.hp;
            delete cube.p;
            delete cube.ba;
            delete cube.bf;
            delete cube.ra;
            delete cube.rf;
            delete cube.ff;
            delete cube.team;
        }

        for (let id in newState.playerData){
            let info = newState.playerData[id];
            if (info){
                info[codeNames.playerReg[14]] = info.lives;
                info[codeNames.playerReg[12]] = info.respawn;
            }
        }
        for (let i in newState.all[4]){
            if (newState.all[4][i]){
                newState.all[4][i][codeNames.deathReg[10]] = newState.playerData;
            }
        }
        return newState;
    }


    // vh down
    // yh up
    // kh rocket
    // Xh bat
    // qh force push
    // Zh grab

    function loadKeys(classi,typ){
        let cons = String(classi.constructor);
        let defines = (cons.split("constructor() {")[1]).split("this.");
        let m = [];
        for (let i of defines){
            m.push(i.split("=")[0]);
        }
        codeNames.keys = m;
    }

    function updateInEditor() {
        document.querySelector("#appContainer > div.cornerButton > div.items > div:nth-child(7)").click();
        document.querySelector("#appContainer > div.lobbyContainer > div.settingsBox > div:nth-child(6)").click();
    }

    function makeInputs(frame,cubes){
        let inputs = stateMaker[codeNames.simulation[1]][codeNames.simulation[2]](frame,true);
        let ts = stateMaker[codeNames.simulation[1]].get(-1);
        if (!codeNames.keys && ts){
            loadKeys(ts);
            codeNames.keySample = ts;
        }
        if (inputs){
            let array = [];
            for (let id in inputs){
                array[id] = {
                    left: inputs[id].left,
                    right: inputs[id].right,
                    up: inputs[id][codeNames.keys[3]],
                    down: inputs[id][codeNames.keys[4]],
                    action3: inputs[id][codeNames.keys[7]], // BAT
                    action4: inputs[id][codeNames.keys[6]], // ROCKET
                    action2: inputs[id][codeNames.keys[8]], // GRAB
                    action1: inputs[id][codeNames.keys[5]] // FP
                }
            }
            for (let id in cubes){
                if (cubes[id]){
                    if (!array[id]){
                        array[id] = {
                            left: false,
                            right: false,
                            up: false,
                            down: false,
                            action3: false, // BAT
                            action4: false, // ROCKET
                            action2: false, // GRAB
                            action1: false // FP
                        }
                    }
                }
            }
            return array;
        }
    }

    const createGraphics = (info) => {
        let id = game.state.graphics.index;
        game.state.graphics.index++;
        game.state.graphics.drawings[id] = info;
        return id;
    }

    //console.log(stateMaker,"won",mostScore)
    const stateVars = String(stateMaker.constructor).match(/this\.(.*?)=/ig);
    stateVars.splice(0,1);
    const stateArray = [];
    for (let i of stateVars) {
        if (i && i.match("=")) {
            stateArray.push(i.split("this.")[1].split("=")[0]);
        }
    }
    // 23
    const Tsettings = stateMaker[stateArray[13]].settings[0]
    const settingsArray = String(Tsettings.constructor).split("constructor() {")[1].match(/this\..{0,2}=(.*?);/ig);
    //console.log(String(Tsettings.constructor));
    const settingsEndArray = [];
    for (let i of settingsArray) {
        if (i.match("=")) {
            settingsEndArray.push(i.split("this.")[1].split("=")[0]);
        }
    }
    codeNames.settings = settingsEndArray;
    console.log(stateArray);
    const editorInfo = stateMaker[stateArray[18]];
    let editorMaps = [];
    const editorVar = String(editorInfo.constructor).match(/this\.(.*?)=/ig);
    editorVar.splice(0,1);
    const editorVarArray = [];
    for (let i of editorVar) {
        if (i && i.match("=")) {
            editorVarArray.push(i.split("this.")[1].split("=")[0]);
        }
    }
    console.log(editorVarArray,"l");
    editorMaps = editorInfo[editorVarArray[4]];
    const stateVars2 = String(stateMaker[stateArray[23]].constructor).match(/this\.(.*?)=/ig);
    // console.log(stateVars2);
    stateVars.splice(0,1);
    const stateArray2 = [];
    for (let i of stateVars2) {
        if (i && i.match("=")) {
            stateArray2.push(i.split("this.")[1].split("=")[0]);
        }
    }
    // console.log(stateArray2);
    // 15
    /*console.log(stateMaker[stateArray[23]]);
    const stateVars3 = String(stateMaker[stateArray[23]][stateArray2[15]].constructor).match(/this\.(.*?)=/ig);
  //  console.log(stateVars3);
    stateVars.splice(0,1);
    const stateArray3 = [];
    for (let i of stateVars3) {
        if (i && i.match("=")) {
         stateArray3.push(i.split("this.")[1].split("=")[0]);
        }
    }*/

    const lerpNumber = function(a, b, weight) {
        return ((1 - weight) * a + weight * b);
    };
    // 0
    // codeNames.deathReg = [stateArray[23],stateArray2[15],stateArray3[0],stateMaker[stateArray[23]][stateArray2[15]][stateArray3[0]]];

    // Stopped here

    /*[
    Ja: {
        "Rr": 0,
        "x": 0,
        "y": 0,
        "color": 16777215,
        "Ir": true,
        "Dr": 0,
        "texture": 0,
        "Lr": 0,
        "Ur": 0,
        "jr": 1,
        "Jr": false,
        "zIndex": 0,
        "Wr": [
            {
                "x": -1,
                "y": -2
            },
            {
                "x": 2,
                "y": 1
            },
            {
                "x": -1,
                "y": 1
            }
        ]
    }
]
*/

    function getWorld(){
        for (let i in stateMaker[codeNames.simulation[3]]){
            if (stateMaker[codeNames.simulation[3]][i].m_island){
                return stateMaker[codeNames.simulation[3]][i];
            }else if (stateMaker[codeNames.simulation[3]][i].PostSolve && !stateMaker[codeNames.simulation[3]][i].injected){
                stateMaker[codeNames.simulation[3]][i].injected = true;
                let a = stateMaker[codeNames.simulation[3]][i];
                const postSolve = a.PostSolve;
                a.PostSolve = function(contact, impulses) {
                    if (impulses.normalImpulses[0] > 0.0) {
                        const worldManifold = new window.Box2D.Collision.b2WorldManifold();
                        contact.GetWorldManifold(worldManifold);
                        /*gmm.collisions.push({
                            fixtureAData: contact.GetFixtureA().GetUserData(),
                            fixtureABodyData: contact.GetFixtureA().GetBody().GetUserData(),
                            fixtureBData: contact.GetFixtureB().GetUserData(),
                            fixtureBBodyData: contact.GetFixtureB().GetBody().GetUserData(),
                            normal: {x: worldManifold.m_normal.x, y: worldManifold.m_normal.y},
                        });*/
                    }

                    return postSolve(...arguments);
                };
            }
        }
    }
    let b2World = getWorld();
    const b2Vec2 = window.Box2D.Common.Math.b2Vec2

    stateMaker.mmR = stateMaker[codeNames.simulation[1]][codeNames.simulation[2]];
    let inputsPropertie = null;
    for (let i in stateMaker[codeNames.simulation[1]]){
        if (stateMaker[codeNames.simulation[1]][i].constructor === Array){
            inputsPropertie = i;
        }
    }
   
    //eval defineGMM("game.events.add('step',function() {game.state.po[0].th = -5;})")

    function getAllStates(){
        let state;
        for (let a in stateMaker){
            let b = stateMaker[a];
            if (b.constructor.name == "Array"){
                for (let i of b){
                    if (typeof(i) == "object" && "all" in i && i.all.constructor.name == "Array"){
                        if (i.all.length > 10 && i.all.length < 15){
                            state = b;
                            break;
                        }

                    }
                }
            }
        }
        if (state){
            return state;
        }
    }

    function setStates(states){
        let state;
        for (let a in stateMaker){
            let b = stateMaker[a];
            if (b.constructor.name == "Array"){
                for (let i of b){
                    if (typeof(i) == "object" && "all" in i && i.all.constructor.name == "Array"){
                        if (i.all.length > 10 && i.all.length < 15){
                            state = b;
                            break;
                        }

                    }
                }
            }
        }
        if (state){
            state = states;
        }
    }

    function getCurrentState(){
        let state;
        for (let a in stateMaker){
            let b = stateMaker[a];
            if (b && b.constructor && b.constructor.name == "Array"){
                for (let it in b){
                    let i = b[it];
                    if (typeof(i) == "object" && "all" in i && i.all.constructor.name == "Array"){
                        if (i.all.length > 10 && i.all.length < 15){
                            state = b;
                            break;
                        }

                    }
                }
            }
        }
        if (state){
            let last;
            for (let a in state){
                state[a].frame = a;
                last = state[a];
            }
            return last;
        }
    }

    function sendInfo(sett = {},offset = 0){
        if (hostId == myid){
            sett.frame = getCurrentState()?.frame-offset;
            settings.nhm = sett;
            WSS.send(`42[1,[62,${JSON.stringify(settings)}]]`)
            WSS.onmessage({data: `42[63,${JSON.stringify(settings)}]`})
        }
    }

    let settings = {};
    let trace = [];
    let tracing = -1;
    let traceLimit = 0;

    function setSett(setts)
    {
        let sett = {};
        let sects = setts.split('|');
        for (let o of sects){
            let pr = o.split(':');
            if (pr[1]){
                let v = JSON.parse(`[${pr[1]}]`)[0];
                sett[pr[0]] = v;
            }
        }
        WSS.onmessage({data: `42[63,${JSON.stringify(sett)}]`})
        WSS.send(`42[1,[62,${JSON.stringify(sett)}]]`)
      }
 
    //<textarea class="scrollBox" wrap="soft" spellcheck="false" style="border: none; outline: none; -webkit-box-shadow: none; -moz-box-shadow: none; box-shadow: none; resize: none; position: absolute; overflow-y: scroll; overflow-x: hidden; background-color: #2f2f2f; height: calc(100% - 60px); width: calc(100% - 80px); left: 80px; top: 50px; box-sizing: border-box; border-bottom-left-radius: 7px; border-bottom-right-radius: 7px; white-space: nowrap;"></textarea>

    let myid = -1;
    let hostId = -1;

    let users = [];
    let abc = 'abcdefghijklmnopqrstuvwxyz';
    const alive = {};
    // Your code here...

    const render = window.PIXI.Text.prototype._render;
    window.PIXI.Text.prototype._render = function(...args){
        render.call(this,...args)
        if (this.parent && this._text) {
                    alive[this._text] = {orbj: this,obj: this.parent,frames: 16, txt: this};
        }
    }

    let frames = 0;
    let lc = Date.now();

    function gCoordinates(x,y){
        let bg = document.getElementById('backgroundImage')
        if (bg){
            let w = bg.clientWidth;
            let h = bg.clientHeight;
            let scale = w/730;
            return [x/scale,y/scale];
        }
        return [0,0];
    }

    function lerp(a, b, x) {
        return a + x * (b - a);
    }

    let lastMO;

    //SP.SE.ve[0].name
    //SP.zE.eo[0];
    let empty = {};

    window.requestAnimationFrame = new Proxy( window.requestAnimationFrame, {
        apply( target, thisArgs, args ) {
            let T = Date.now();
            let dt = (T-lc)/1000;
            lc = T;
            frames++
            Reflect.apply(...arguments);
            /*if (currentState && currentState.mo){
            for (let id in currentState.mo){
             let info = currentState.mo[id];
                if (!info.injected){
                    info.injected = true;
                    let player = findUser(info.$h);
                    console.log(player.name,"died?",info);
                }
            }
        }*/

            for (let i in alive) {
                let unalive = (!alive[i].obj || !alive[i].obj.transform || !alive[i].obj.parent || !alive[i].txt || !alive[i].txt.visible || alive[i].txt.parent != alive[i].obj || !alive[i].obj.visible || alive[i].obj.alpha <= 0);
                let p = findUser(i);
                if (p){
                    if (unalive){
                        alive[i].frames--
                        if (alive[i].frames <= 0){
                            delete alive[i];
                        }
                    }else{

                    }
                }else{
                    delete alive[i];
                }
            }
        }
    })

    const originalSend = window.WebSocket.prototype.send;
    let excludewss = [];
    let WSS = 0;

    function findUser(id){
        for (let t in users) {
            let o = users[t];
            if (o.id == id || o.name == id){
                o.index = t;
                return o;
                break;
            }
        }
    }

    //eval setInterval(() => {sendInfo({execute:`this.state.po[0].th = -20;`});},2000);

    function decodeString(encodedString){
        let decompressed = atob(decodeURIComponent(encodedString));
        let inflated = pako.inflate(decompressed, {
            '\x74\x6f': "string"
        });
        let decoded = JSON.parse(inflated);
        return decoded;
    }

    window.WebSocket.prototype.send = function(args) {
        if(this.url.includes("/socket.io/?EIO=3&transport=websocket&sid=")){
            if(typeof(args) == "string" && !excludewss.includes(this)){
                if (!WSS){
                    WSS = this;
                }
                if (WSS == this){
                    if (args.startsWith('42[1,[')) {
                        try{
                            let packet = JSON.parse(args.slice(5,-1))
                            if (packet[0] == 62){
                                settings = packet[1];
                            }
                        }catch(error){}
                    }else if (args.startsWith('42[2,')) {
                        myid = 0;
                        hostId = 0;
                    }
                }else{
                    excludewss.push(this);
                }
                //console.log('SENT',args);
            }
            if (!this.injectedNCE){
                this.injectedNCE = true;
                const originalClose = this.onclose;
                this.onclose = (...args) => {
                    if (WSS == this){
                        WSS = 0;
                        excludewss = [];
                        users = [];
                    }
                    originalClose.call(this,...args);
                }
                this.onmessage3 = this.onmessage;
                this.onmessage = function(event){
                    if(!excludewss.includes(this) && typeof(event.data) == 'string'){
                        if (event.data.startsWith('42[')){
                            let packet = JSON.parse(event.data.slice(2,event.data.length));
                            if (packet[0] == 63){
                                settings = packet[1];
                            }
                            if (packet[0] == 7){
                                myid = packet[1][0]
                                hostId = packet[1][1];
                                for (let i of packet[1][3]){
                                    users.push({"team": i[2],"color":(i[7][0] || i[7][1]),"name":i[0],"id":i[4],"lvl":i[6]});
                                }
                            }
                            if (packet[0] == 25){
                                let plr = findUser(packet[1]);
                                if (plr){
                                    plr.team = packet[2];
                                }
                            }
                            if (packet[0] == 9){
                                hostId = packet[2];
                                let user = findUser(packet[1]);
                                if (user){
                                    users.splice(user.index,1);
                                }
                            }
                            if (packet[0] == 45){
                                hostId = packet[1];
                            }
                            if (packet[0] == 8){
                                users.push({"name":packet[1][0],"color":(packet[7]? (packet[7][1] || packet[7][0]):undefined),"team":packet[1][2],"id":packet[1][4],"lvl":packet[1][6]});
                            }
                        }
                    }
                    this.onmessage3.call(this,event);
                }
            }
        }
        return originalSend.call(this, args);
    }

    let chats = document.getElementsByClassName('content');
    window.addEventListener('keydown',(event) => {

    });

    window.hescape = (s) => {
        let lookup = {'$':'&#36;','%':'&#37;','.':'&#46;','+':'&#43;','-':'&#45;','&':"&amp;",'"': "&quot;",'\'': "&apos;",'<': "&lt;",'*':'&#42;','=':'&#61;','>': "&gt;",'#':'&#35;',':':'&#58;',';':'&#59;','`':'&#96;'};
        return s.replace( /[\*=%#\-+&"'<>]/g, c => lookup[c] );
    }

    var lastMousePos = {x: 0,y: 0};

    window.addEventListener("mousemove",(e) => {
        e = e || window.event;
        let pos1 = lastMousePos.x || e.clientX;
        let pos2 = lastMousePos.y || e.clientY;
        lastMousePos = {x: e.clientX,y: e.clientY};
        if (document.activeElement && document.activeElement.dataset.dragable){
            e.preventDefault();
            document.activeElement.style.top = (document.activeElement.offsetTop + (e.clientY-pos2)) + "px";
            document.activeElement.style.left = (document.activeElement.offsetLeft + (e.clientX-pos1)) + "px";
        }
    });

    function getRGBFromNUM(colorID,offset,max){
        const red = (colorID >> 16) & 0xFF;
        const green = (colorID >> 8) & 0xFF;
        const blue = colorID & 0xFF;

        // Construct the RGB color representation
        return `rgb(${Math.max(max || 0,red-(offset || 0))}, ${Math.max(max || 0,green-(offset || 0))}, ${Math.max(max || 0,blue-(offset || 0))})`;
    }

    function display(text,ingamecolor,lobbycolor,sanitize){
        if (WSS){
            let div = document.createElement('div');
            div.classList.add('statusContainer');
            let span = document.createElement('span');
            span.classList.add('status');
            span.style.color = lobbycolor || "#ffffff";
            if (sanitize != false){
                span.textContent = text;
            }else{
                span.innerHTML = text;
            }
            span.style.backgroundColor = 'rgba(37, 38, 42, 0.768627451)';
            div.style.borderRadius = '7px';
            div.appendChild(span);
            let clone = div.cloneNode(true);
            clone.children[0].style.color = ingamecolor || '#ffffff';
            setTimeout(() => {
                clone.remove();
            },11500);
            for (let i of chats){
                if (i.parentElement.classList.contains('chatBox')){
                    i.appendChild(div);
                    i.scrollTop = Number.MAX_SAFE_INTEGER;
                }else{
                    i.appendChild(clone);
                }
            }
        }
    }

    function updateEditor() {
        document.querySelector("#editorContainer > div.topMenu > div.topLabel.fileMenu > div > div:nth-child(5)").click();
        document.querySelector("#appContainer > div.lobbyContainer > div.settingsBox > div:nth-child(6)").click();
    }

    let windowContent;
    let windowTopProperties;

    function setPropertiesName(title) {
        let closeClick = windowTopProperties.children[0].onclick;
        let minimizeClick = windowTopProperties.children[1].onclick;
        windowTopProperties.innerHTML = windowTopProperties.innerHTML.replace("Merge Shapes",title);
        windowTopProperties.children[0].onclick = closeClick;
        windowTopProperties.children[1].onclick = minimizeClick;
    }

    let fields = 0;

    function addPropertiesField(title,description) {
        let div = document.createElement('div');
        div.classList.add("row");
        fields += 1;
        if (fields % 2 == 0) {
            div.classList.add("bgalt");
        }
        windowContent.appendChild(div);
        div.innerHTML = `<span class="title">${title}</span><span class="subtitle">${description}</span><input>`;
        return div;
    }

     function addPropertiesButton(title) {
        let div = document.createElement('div');
        div.classList.add("row");
         windowContent.appendChild(div);
        div.innerHTML = `<button>${title}</button>`;
        return div;
    }

    function setAdvice(advice) {
     document.querySelector("#relativeContainer > div").textContent = advice;
    }

    function openProperties() {
        document.querySelector("#editorContainer > div.topMenu > div.topLabel.toolsMenu > div > div:nth-child(1)").click();
        windowTopProperties = document.querySelector("#editorPropertiesWindow > div.topBar");
        windowContent = document.querySelector("#editorPropertiesWindow > div.contentDiv");
        windowContent.innerHTML = '';
    }

    function scaleBody(bodyId,sampleX,sampleY,sample) {
        updateEditor();
        for (let i in editorMaps[0].state.all[5][bodyId].Sa) {
            let p = editorMaps[0].state.all[5][bodyId].Sa[i];
            if (p) {
                p.x *= sampleX;
                p.y *= sampleY;
                p.ra *= sample;
                for (let i in p.ca) {
                    let z = p.ca[i];
                    if (z) {
                        z.x *= sampleX;
                        z.y *= sampleY;
                    }
                }
            }
        }
        updateInEditor();
    }

    const editorTools = document.querySelector("#editorContainer > div.topMenu > div.topLabel.toolsMenu > div");
    let scaleBodyTool = document.createElement('div');
    editorTools.appendChild(scaleBodyTool);
    let copyMap = document.createElement('div');
    editorTools.appendChild(copyMap);
    copyMap.textContent = 'Copy Map';
    copyMap.classList.add("item");
    copyMap.onclick = () => {
document.querySelector("#editorContainer > div.topMenu > div.topLabel.fileMenu > div > div:nth-child(3)").click();
        setAdvice("Saving map...");
        document.querySelector("#appContainer > div.mapListContainer").style.display = 'none';
        new Promise((r,f) => {
let intervalID = setInterval(() => {
    if (document.querySelector("#appContainer > div.mapListContainer > div.mapList > div.mapsContainer > div:nth-child(1)")) {
        r();
        clearInterval(intervalID);
    }
},0);
        })
        .then(() => {
         document.querySelector("#appContainer > div.mapListContainer > div.mapList > div.mapsContainer > div:nth-child(1)").click();
            document.querySelector("#appContainer > div.mapListContainer > div.mapList > div.enterNameWindow > input").value = "#"+Math.floor(Math.random()*1000)+" by " + editorMaps[0].BN;
            setAdvice("Map saved as "+document.querySelector("#appContainer > div.mapListContainer > div.mapList > div.enterNameWindow > input").value);
            document.querySelector("#appContainer > div.mapListContainer > div.mapList > div.enterNameWindow > textarea").value = "This map was copied using NCE.";
            document.querySelector("#appContainer > div.mapListContainer > div.mapList > div.enterNameWindow > select").value = 0;
            document.querySelector("#appContainer > div.mapListContainer > div.mapList > div.enterNameWindow > div.button.okButton").click();
            document.querySelector("#editorContainer > div.topMenu > div.topLabel.fileMenu > div > div:nth-child(3)").classList.add("disabled");
            editorMaps[0].BN = 'COPIED';
            editorMaps[0].FN = 0;
            editorMaps[0].IN = true;
        })
    }
    scaleBodyTool.textContent = 'Scale Body';
    scaleBodyTool.classList.add("item");
    scaleBodyTool.onclick = () => {
        openProperties();
        setPropertiesName("scale Body");
        const bodyId = addPropertiesField("Source Body ID","The body to be scaled:");
        const sample = addPropertiesField("Scale Sample","The scale used for circles:");
        const sampleX = addPropertiesField("Scale Sample X","The scale used for X axis:");
        const sampleY = addPropertiesField("Scale Sample Y","The scale used for Y axis:");
        const buttton = addPropertiesButton("Scale");
        buttton.children[0].onclick = () => {
            scaleBody(bodyId.children[2].value,sampleX.children[2].value,sampleY.children[2].value,sample.children[2].value);
        }
    };

    let editorDiv = document.querySelector("#appContainer > div.lobbyContainer > div.settingsBox > div.editorButton.settingsButton");

});

QingJ © 2025

镜像随时可能失效,请加Q群300939539或关注我们的公众号极客氢云获取最新地址