Better player info.

The best way to spy on others resources!

当前为 2022-02-12 提交的版本,查看 最新版本

// ==UserScript==
// @name         Better player info.
// @namespace    http://tampermonkey.net/
// @version      0.4
// @description  The best way to spy on others resources!
// @author       Diamondkingx
// @match        http://zombs.io/
// @icon         https://www.google.com/s2/favicons?domain=zombs.io
// @grant        none
// @license      GNU GPLv3
// ==/UserScript==
//Alt + Hover a Player to activate!
//You could change a lot of stuff from line: 424, Go try it out
let CSS = `
:root{
--spectatemenu-buttons-width:90%;
--spectatemenu-buttons-height:24%;
--spectatemenu-buttons-icon-width:10%;
--spectatemenu-buttons-icon-height:100%;
--spectatemenu-buttons-name-top:10%;
--spectatemenu-buttons-name-left:12%;
--spectatemenu-buttons-name-fontSize:17px;
--spectatemenu-buttons-rank-bottom:2%;
--spectatemenu-buttons-rank-left:12%;
--spectatemenu-buttons-rank-fontSize:15px;
}
.mainMenu{
    width: 360px;
    height: 180px;
    position: absolute;
    transform: scale(0) rotate(0deg);
    pointer-events: all;
    z-index: 5;
    transition: all 0.3s;
}
.menu {
    width: 100%;
    height: 110%;
    position: absolute;
    left: -50%;
    top: 50%;
    z-index: 1;
    color: rgba(255, 255, 255, 0.8);
    opacity: 0;
    background: rgba(0, 0, 0, 0.4);
    border-radius: 4px;
    transform: translate(-50%, -45%);
    transition: all 0.3s;
    pointer-events: none;
    overflow: hidden;
}
.activateMenuButtonsContainer {
    width: 30px;
    height: auto;
    position: absolute;
    left: 100%;
    top: 98%;
    padding: 20px;
    transform: translateY(-50%);
    padding-top: 2px;
    padding-bottom: 7px;
    background: rgba(0, 0, 0, 0.4);
    border-radius: 4px;
    border-bottom-left-radius: 0;
    border-top-left-radius: 0;
    transition: all 0.2s;
    overflow: hidden;
}
.activateMenuButtonsContainer button {
    width: inherit;
    height: 30px;
    position: relative;
    left: 50%;
    background: rgba(0, 0, 0, 0.2);
    transform: translate(-50%, 6%);
    border-radius: inherit;
    border: none;
    outline: none;
    cursor: pointer;
    pointer-events: all;
    margin-top: 2px;
    transition: all 0.3s;
}
.activateMenuButtonsContainer button span {
    width: 100%;
    height: 100%;
    position: absolute;
    top: -22%;
    left: 24%;
    background-size: 27px;
    background-repeat: no-repeat;
    transform: rotate(
    -130deg);
    opacity: 0.7;
    transition: all 0.3s;
    pointer-events: none;
}
.activateMenuButtonsContainer button:hover{
   background: rgba(255,255,255,0.05);
}
.activateMenuButtonsContainer button:hover > span {
    opacity: 0.9;
 }
.arrowButton {
    width: 60px;
    height: 40px;
    position: absolute;
    top: 89%;
    left: 87.5%;
    z-index: 1;
    font-weight: bold;
    color: rgba(255, 255, 255, 0.7);
    font-family: Hammersmith One;
    font-size: 20px;
    background-color: transparent;
    border: none;
    outline: none;
    overflow: hidden;
    transition: left 0.5s, top 0.5s, opacity 0.3s;
}
.arrowButton p:hover {
    color: rgba(255, 255, 255, 1);
}
.arrowButton p {
    width: 60%;
    position: absolute;
    top: 0%;
    left: 50%;
    cursor: pointer;
    transition: all 0.5s;
    transform: translate(-50%, -50%) rotateY(0deg);
}
.petNotFound {
    width: 100%;
    height: 100%;
    background-color: transparent;
    position: absolute;
    top: 50%;
    left: 50%;
    transform: translate(-50%, -50%);
    border-radius: 5px;
}
.spinner {
    animation: spin 0.4s infinite ease-in-out;
}
.healthbars-container {
    height: 130px;
    position: absolute;
    display: flex;
    align-content: center;
    flex-wrap: wrap;
    justify-content: center;
    transition: all 0.2s;
  }
.playerHealth {
    position: absolute;
    top: 18%;
    left: 41%;
    display: none;
    color: #eee;
    font-size: 12px;
    font-family: "Hammersmith One", sans-serif;
    line-height: 27px;
    text-shadow: 0 0 1px rgb(0 0 0 / 80%);
    transform: translate(-50%, -50%);
}
.spectatemenu-button{
    width: var(--spectatemenu-buttons-width);
    height: var(--spectatemenu-buttons-height);
    position: relative;
    left: 5%;
    top: 0%;
    background: rgba(255,255,255,0.08);
    border-radius: 6px;
    border: none;
    outline: none;
    overflow: hidden;
    margin-bottom: 9px;
    transition: top 0.5s, background 0.3s, width 0.5s, height 0.2s, opacity 0.5s;
    pointer-events: all;
    cursor: pointer;
    z-index: 2;
    opacity: 0;
}
.spectatemenu-button:hover{
    background: rgba(255,255,255,0.16);
}
.spectatemenu-icon{
    width: var(--spectatemenu-buttons-icon-width);
    height: var(--spectatemenu-buttons-icon-height);
    background: rgba(255,255,255,0.25);
    position: absolute;
    left: 0%;
    top: 0%;
    display: grid;
    align-items: center;
}
.spectatemenu-icon i {
    font-size: 32px;
    color: rgba(255,255,255,1);
    transition: all 0.25s;
}
.spectatemenu-name{
    position: absolute;
    top: var(--spectatemenu-buttons-name-top);
    left: var(--spectatemenu-buttons-name-left);
    font-size: var(--spectatemenu-buttons-name-fontSize);
    font-family: 'Hammersmith One';
    color: rgba(255,255,255,0.8);
    border-bottom: 0px solid rgba(255,255,255,0.4);
    width: 89%;
    overflow-y: hidden;
 }
.spectatemenu-rank{
    position: absolute;
    bottom: var(--spectatemenu-buttons-rank-bottom)%;
    left: var(--spectatemenu-buttons-rank-left);
    font-size: var(--spectatemenu-buttons-rank-fontSize);
    font-family: 'Hammersmith One';
    color: rgba(255,255,255,0.6);
}
.spectatemenu-background{
    width: 94.5%;
    height: 80%;
    position: absolute;
    top: 5%;
    background: rgba(0,0,0,0.2);
    border-radius: 5px;
    z-index: 1;
}
.spectatemenu-spectating{
    position: absolute;
    top: 95%;
    left: 71%;
    color: rgba(255,255,255,0.7);
    font-weight: normal;
    font-family: 'Hammersmith One';
    z-index: -1;
    opacity: 0;
}
.label {
  color: #EAFAF1;
  position: absolute;
  top: -40%;
  left: 3.5%;
  font-weight: normal;
}
.coloured-div {
  width: 290px;
  height: 30px;
  left: 3.5%;
  top: 40%;
  background: rgba(71, 149, 13, 1);
  position: absolute;
  border-top-left-radius: 5px;
  transition: all 0.3s;
}
.text-div {
  background: transparent;
  width: 95%;
  heigth: 80%;
  transform: translate(-50%, -50%);
  position: absolute;
  top: 50%;
  left: 50%;
  border-radius: 4px;
  text-align: justify;
}
.text-div p, .text-div span {
  font-size: 13px;
  color: #EAFAF1;
  font-family: "Hammersmith One";
  position: absolute;
  top: -50%;
  left: -1%;
}
.text-div i {
  color: rgba(234, 250, 241, 0.8);
  position: relative;
  left: 95%;
  transform: translateY(-5%);
  cursor: pointer;
  transition: color 0.2s;
}
.text-div i:hover{
  color: rgba(234, 250, 241, 1);
}
.errors {
  position: absolute;
  font-size: 64%;
  left: 48%;
  top: -18%;
  color: #EAFAF1;
  opacity: 0;
  background: rgba(0, 0, 0, 0.8);
  border-radius: 3px;
  padding-left: 1.2%;
  padding-right: 1.2%;
  padding-top: 0.4%;
  padding-bottom: 0.4%;
  transition: all 0.2s;
}
.notificationsContainer{
  width: 300px;
  height: 300px;
  position: absolute;
  top: 0px;
}
.notification-main {
  width: 300px;
  height: auto;
  position: relative;
  left: -100%;
  top: 0%;
  min-height: 50px;
  background: rgba(0, 0, 0, 0.4);
  border-top-right-radius: 6px;
  border-bottom-right-radius: 6px;
  overflow: hidden;
  z-index: 16;
  transition: all 0.75s;
}

.notification-label {
  position: relative;
  left: 3%;
  color: #EAFAF1;
  font-family: 'Hammersmith One';
  font-size: 15px;
  font-weight: normal;
  margin: 0px;
  margin-top: 1%;
  margin-bottom: 1%;
}

.notification-background {
  width: 97%;
  height: auto;
  min-height: 30px;
  position: relative;
  left: 3%;
  background: rgb(71, 149, 13);
  display: grid;
  align-items: center;
  border-top-left-radius: 5px;
}

.notification-text {
  width: 80%;
  position: relative;
  left: 2%;
  color: #EAFAF1;
  font-size: 13px;
  font-family: 'Hammersmith One';
  font-weight: normal;
  word-break: break-all;
}
.notification-errors {
  position: absolute;
  left: 43%;
  top: -69%;
  font-size: 11px;
  font-family: 'Hammersmith One';
  color: #fff;
  background: rgba(0, 0, 0, 0.4);
  display: grid;
  align-items: center;
  border-radius: 3px;
  padding-left: 3px;
  padding-top: 1px;
  padding-bottom: 1px;
  padding-right: 3px;
  opacity: 0;
}

.notification-errors span {
  position: relative;
  top: 7%;
}
.notification-Icon{
  position: absolute;
  left: 92%;
  color: rgba(234, 250, 241, 0.8);
  transform: translateY(-5%);
  transition: all 0.3s;
  cursor: pointer;
}
.notification-Icon:hover{
  color: rgba(250, 250, 250, 1);
}
.hud-building-overlay .shield-bar::after {
    content: "SHIELD";
}
.hud-building-overlay .hud-tooltip-health{
    display: block;
    position: absolute;
    width: 100px;
    height: 34px;
    padding: 4px;
    background: rgba(0, 0, 0, 0.2);
    border-radius: 4px;
    margin-top: 1px;
}
.hud-building-overlay .hud-building-stats .hud-stats-values:first-child::after {
    display: none;
}
.hud-tooltip-top::after {
    display: none;
}
/* .hud-building-overlay .hud-tooltip-health::after {} */
@keyframes spin {
    from {
        transform: rotate(0deg);
    }
    to {
        transform: rotate(360deg);
    }
}
`;
let style = document.createElement("style");
document.head.appendChild(style);
style.appendChild(document.createTextNode(CSS));
//This is the main variable that could lead to breaking the whole script, When making unknown changes
var main = {
  properties: {
    showNotifications: true,
    //Turn this off if you don't want notifications
    activePlayerUid: 0,
    //This will check which uid is currently selected by the player
    displayMainMenu: false,
    //This will tell if the main menu is visible
    allowMouseMove: false,
    //This will change true if you are holding alt
    allowVisibilityChange: true,
    //This changes the opacity of the main menu as it goes above other elements or comes below other elements Ex: Opening chat, Opening settings or Going above chat
    allowRetrack: true,
    isSpectating: false,
    currentMenu: "mainMenu",
    playerTracker: {
      cursorSize: 15, //Changing this to astronomical units won't help
      mainPlayer: {},
      targetedPlayer: {},
    },
    //This will check and tell the position of the mouse and the distance for the mainplayer and targetedPlayer
    updater: {
      calculationProcesses: {
        lastFrameTime: 0,
        timeSinceLastFrame: 0,
        FPSstored: 0,
        storedFPStime: new Date(),
      },
      clientProcesses: {
        FPSlimit: 30, //Change this for either higher FPS or lower, Default 30
        currentFPS: 0,
      },
    },
    //This is the updater that updates the inforamation in the script
    transitions: {
      menusButtonsContainerClose: 750,
    },
    iconHandler: {
      //This handles the icons and has 2 FPS
      FPS: 2, //Changing this could make some transitions look odd
      lastFrameTime: 0,
      timeSinceLastFrame: 0,
      mainFunction: function (timeStamp) {
        this.timeSinceLastFrame = timeStamp - this.lastFrameTime;
        if (this.timeSinceLastFrame >= 1000 / this.FPS) {
          this.lastFrameTime = timeStamp;
          if (
            main.properties.activePlayerUid !== 0 &&
            game.network.connected &&
            game.world.inWorld
          ) {
            main.accessableElements.menusButtonsContainer.style.top = `${
              96 -
              (main.accessableElements.menusButtonsContainer.info.properties.getVisibleButtons() -
                1) *
                10
            }%`;
            if (
              game.world.entities[main.properties.activePlayerUid] !==
                undefined &&
              game.world.entities[
                game.world.entities[main.properties.activePlayerUid].targetTick
                  .petUid
              ]
            ) {
              if (
                game.world.entities[
                  game.world.entities[main.properties.activePlayerUid]
                    .targetTick.petUid
                ]?.isInViewport()
              ) {
                main.properties.global.pet =
                  game.world.entities[
                    game.world.entities[
                      main.properties.activePlayerUid
                    ].targetTick.petUid
                  ];
              }
            } else main.properties.global.pet = null;
          }
          let icons = main.icons;
          icons.forEach((icon) => {
            let id = icon.for;
            let element;
            main.accessableElements.menusButtonsContainer
              .querySelectorAll("button")
              .forEach((button) => {
                button.className.toUpperCase().includes(id.toUpperCase())
                  ? (element = button)
                  : null;
              });
            if (icon.check()) {
              element.style.transform = "translate(-50%, 6%) scale(1)";
              element.style.position = "relative";
              element.getElementsByTagName(
                "span"
              )[0].style.backgroundImage = `url(${icon.check()})`;
            } else {
              element.style.transform = "translate(-50%, 6%) scale(0)";
              setTimeout(() => {
                element.style.position = "absolute";
              }, 150);
            }
            icon.do?.(element);
          });
          if (
            main.accessableElements.menusButtonsContainer.info.properties.getVisibleButtons() ==
              0 &&
            main.accessableElements.transitionMenus.info.properties.state ==
              "default" &&
            !main.properties.isSpectating
          ) {
            if (
              main.accessableElements.menusButtonsContainer.info.properties
                .active
            ) {
              setTimeout(() => {
                if (
                  main.accessableElements.menusButtonsContainer.info.properties.getVisibleButtons() ==
                  0
                ) {
                  main.accessableElements.menusButtonsContainer.info.properties.deactivated();
                }
              }, main.properties.transitions.menusButtonsContainerClose);
            }
            main.accessableElements.arrowButton.style.pointerEvents = "none";
            main.accessableElements.arrowButton.style.opacity = "0.33";
            main.accessableElements.transitionMenus.info.properties.state =
              "default";
            setTimeout(() => {
              if (
                main.accessableElements.menusButtonsContainer.info.properties.getVisibleButtons() ==
                0
              ) {
                main.accessableElements.arrowButton.info.properties.deactivated();
              }
            }, main.properties.transitions.menusButtonsContainerClose);
          } else {
            main.accessableElements.arrowButton.style.pointerEvents = "all";
            main.accessableElements.arrowButton.style.opacity = "1";
          }
          if (
            main.accessableElements.transitionMenus.info.properties.state
              .toUpperCase()
              .includes("SPECTATE") &&
            main.accessableMenus.spectateMenu.getAllMembers() <= 0 &&
            !main.properties.isSpectating
          ) {
            main.accessableElements.arrowButton.info.properties.deactivated();
          }
          if (
            game.world.entities[main.properties.activePlayerUid] !==
              undefined &&
            main.properties.activePlayerUid !== undefined
          ) {
            if (
              game.world.entities[
                game.world.entities[main.properties.activePlayerUid].targetTick
                  .petUid
              ] == undefined &&
              main.accessableElements.transitionMenus.info.properties.state
                .toUpperCase()
                .includes("PET")
            ) {
              main.accessableElements.arrowButton.info.properties.deactivated();
            }
          }
          if (
            main.accessableElements.transitionMenus.info.properties.state ==
            "spectateMenu"
          ) {
            handleSpectateButtonStyle();
          }
          main.accessableElements.mainMenu.info.properties.checkVisibilityState();
        }
        if (main.properties.allowVisibilityChange) {
          if (
            !main.accessableElements.mainMenu.info.properties.otherMenusActive()
          ) {
              if(window.mainMenuX && window.mainMenuY){
            if (
              parseInt(mainMenuX) <
                0 + main.accessableElements.mainMenu.offsetWidth ||
              parseInt(mainMenuX) >
                window.innerWidth -
                  main.accessableElements.mainMenu.offsetWidth * 2 ||
              parseInt(mainMenuY) >
                window.innerHeight -
                  main.accessableElements.mainMenu
                    .getElementsByClassName("hud-building-overlay")[0]
                    .getBoundingClientRect().height *
                    1.6
            ) {
              main.accessableElements.mainMenu.info.properties.visibility =
                "dark";
            } else {
              main.accessableElements.mainMenu.info.properties.visibility =
                "default";
            }
              }
          } else {
            main.accessableElements.mainMenu.info.properties.visibility =
              "light";
          }
        }
        //I don't think this ONLY handle's icons now...
      },
    },
    notificationsHandler: {
      queuedNotifications: [],
      updater: {
        FPS: 12,
        timeSinceLastFrame: 0, //Ik, I am repeating this a lot of times now... But I don't care
        lastFrameTime: 0,
        main: function (timeStamp) {
          this.timeSinceLastFrame = timeStamp - this.lastFrameTime;
          if (this.timeSinceLastFrame >= 1000 / this.FPS) {
            this.lastFrameTime = timeStamp;
            main.properties.notificationsHandler.queuedNotifications =
              main.properties.notificationsHandler.queuedNotifications.filter(
                (notification) => !notification.isLooked
              );
            main.properties.notificationsHandler.queuedNotifications.forEach(
              (notification) => {
                //Stuff here afterwards/Next updates
              }
            );
          }
        },
      },
    },
    global: {
      pet: undefined,
    },
    retargetAfter: 50,
    //This defines how fast the script will check if the cursor is above a player
  },
  accessableElements: {
    hud: document.getElementsByClassName("hud")[0],
  },
  modularFunctions: {
    arrayToHTML: (array) => {
      let elementsArray = array
          ? array
          : [
              {
                name: "undefined",
                type: "p",
                attributes: {
                  innerHTML: `nope`, //Nope, Get rekt
                },
                parent: document.body,
              },
            ],
        scannedElements = [];
      elementsArray.forEach((element) => {
        let ele = document.createElement(element.type);
        ele.name = element.name;
        ele.parent = element.parent;
        if (element["attributes"]) {
          let value = element["attributes"];
          Object.keys(value).forEach((property) => {
            let propertyValue = value[property];
            if (ele[property] !== undefined) {
              ele[property] = propertyValue;
            }
          });
        }
        element.element = ele;
        ele.info = element;
        main.accessableElements[element.name] = ele;
        scannedElements.push(ele);
      });
      scannedElements.forEach((sElement) => {
        if (typeof sElement.parent == "string") {
          if (
            scannedElements.find((element) => element.name == sElement.parent)
          ) {
            scannedElements
              .find((element) => element.name == sElement.parent)
              .append(sElement);
          } else {
            throw new SyntaxError(
              `Append on unknown parent ${sElement.parent}`
            );
          }
        } else if (typeof sElement.parent == "function") {
          sElement.parent().append(sElement);
        } else {
          sElement.parent.append(sElement);
        }
      });
    },
    //👆I love objects
    numberToSI: (number) => {
      var symbols = ["", "k", "M", "G", "T", "P", "E"],
        tier = (Math.log10(Math.abs(number)) / 3) | 0;
      if (tier == 0) return number;
      var suffix = symbols[tier],
        scale = Math.pow(10, tier * 3),
        scaled = number / scale;
      return scaled.toFixed(1) + suffix;
    },
    //👆Yea, I copied this from stack overflow
    onEnteringGame: () => {
      function main() {
        if (game.network.connected && game.world.inWorld)
          new customNotification("Everything Looks Good!");
        else
          setTimeout(() => {
            main();
          }, 100);
      }
      main();
    },
    //👆Idk how to use game.world.onEnterWorld
    inChat: () => {
      if (
        document
          .getElementsByClassName("hud")[0]
          .getElementsByClassName("hud-chat")[0]
          .className.includes("is-focused")
      ) {
        return true;
      } else {
        return false;
      }
    },
    //👆Is there a better way??
    handleSingleUseFunctions: function (object) {
      if (!"singleUseFunctions" in object) return;
      Object.keys(object["singleUseFunctions"]).forEach((Function) => {
        object["singleUseFunctions"][Function]?.();
      });
      delete object["singleUseFunctions"];
    },
    //👆I added this for a reason will use in further updates
  },
  elements: [
    //👇THE BEST WAY OF DEFINING HTML ELEMENTS IN JS!!! Atleast for me
    {
      name: "mainMenu",
      type: "div",
      attributes: {
        className: "mainMenu",
        innerHTML: `
           <link
  rel="stylesheet"
  href="https://use.fontawesome.com/releases/v5.15.4/css/all.css"
  integrity="sha384-DyZ88mC6Up2uqS4h/KRgHuoeGwBcD4Ng9SiP4dIRy0EXTlnuz47vAwmeGwVChigm"
  crossorigin="anonymous"
/>
<div
  id="hud-building-overlay"
  class="hud-building-overlay hud-tooltip hud-tooltip-top info-container"
  style="display: block; left: 0px; top: 0px; transition: all 0.4s; z-index: 1; overflow-y: hidden;"
>
  <div class="hud-tooltip-building">
    <h2 class="player-Name" style="overflow-y: hidden;">undefined</h2>
    <h3 style="position: relative; left: 0px">
      Uid: <span class="hud-building-tier player-Uid">1</span>
    </h3>
    <ul class="healthbars-container" style="left: 60%; top: -24%">
      <li class="hud-tooltip-health" style="position: relative;">
        <span
          class="hud-tooltip-health-bar"
          style="
            width: 100%;
            transition: all 0.2s;
            background: #64a10a;
          "
        ></span>
      </li>
      <li class="hud-tooltip-health shield-bar" style="position: relative;">
        <span
          class="hud-tooltip-health-bar"
          style="
            width: 100%;
            transition: all 0.2s;
            background: #3da1d9;
            display: none;
          "
        ></span>
      </li>
    </ul>
    <div class="hud-tooltip-body">
      <div class="hud-building-stats">
        <div class="hud-stats-current hud-stats-values">
          <p>
            Wood:
            <strong class="hud-stats-current player-Wood">undefined</strong>
          </p>
          <p>
            Stone:
            <strong class="hud-stats-current player-Stone">undefined</strong>
          </p>
          <p>
            Gold:
            <strong class="hud-stats-current player-Gold">undefined</strong>
          </p>
        </div>
        <div class="hud-stats-next hud-stats-values">
          <p>
            Tokens:
            <strong class="hud-stats-next player-Tokens">undefined</strong>
          </p>
          <p>
            Score:
            <strong class="hud-stats-next player-Score">undefined</strong>
          </p>
          <p style="display: block">
            Health:
            <strong class="hud-stats-next player-Health">undefined</strong>
          </p>
        </div>
      </div>
      <p class="hud-building-actions" style="display: block">
        <span class="hud-building-dual-btn" style="display: none"> </span>
      </p>
    </div>
  </div>
</div>
`,
      },
      parent: document.getElementsByClassName("hud")[0],
      properties: {
        visibility: "default",
        closedThrough: function (inputType) {
          function callback() {
            if (main.properties.isSpectating) {
              let spectateMenu = main.availableMenus.find((menu) =>
                menu.id.toUpperCase().includes("SPECTATE")
              );
              spectateMenu.deactivated();
            }
            main.accessableElements.mainMenu.style.transform = "scale(0)";
            main.accessableElements.mainMenu.style.pointerEvents = "none";
            main.accessableElements.transitionMenus.info.properties.state =
              "default";
            main.accessableElements.transitionMenus.style.opacity = "0";
            main.accessableElements.transitionMenus.style.left = "-50%";
            main.accessableElements.transitionMenus.style.pointerEvents =
              main.accessableElements.menusButtonsContainer.info.properties.deactivated();
            ("none");
            main.accessableElements.arrowButton.style.left = "87.5%";
            main.accessableElements.arrowButton.getElementsByTagName(
              "p"
            )[0].style.transform = "translate(-50%,-50%) rotateY(0deg)";
            main.properties.displayMainMenu = false;
          }
          if (inputType.toUpperCase() == "CLICKED") {
            if (
              !main.accessableElements.mainMenu.contains(
                main.cursor.client.target
              )
            ) {
              callback();
            }
          }
          if (inputType.toUpperCase() == "SHIFTKEY") {
            if (main.modularFunctions.inChat() == false) {
              callback();
            }
          }
        },
        scale: function () {
          let menuMaxWidth = main.accessableElements.mainMenu.offsetWidth,
            menuMaxHeight = main.accessableElements.mainMenu.offsetHeight;
          return {
            x:
              (((menuMaxWidth -
                (menuMaxWidth -
                  main.accessableElements.mainMenu.getBoundingClientRect()
                    .width)) /
                menuMaxWidth) *
                100) /
              100,
            y:
              (((menuMaxHeight -
                (menuMaxHeight -
                  main.accessableElements.mainMenu.getBoundingClientRect()
                    .height)) /
                menuMaxHeight) *
                100) /
              100,
          };
        },
        checkVisibilityState: function () {
          switch (this.visibility) {
            case "default":
              main.accessableElements.mainMenu.style.opacity = "1";
              main.accessableElements.mainMenu.style.filter = "";
              break;
            case "light":
              main.accessableElements.mainMenu.style.opacity = "0.5";
              main.accessableElements.mainMenu.style.filter = "";
              break;
            case "dark":
              main.accessableElements.mainMenu.style.opacity = "1";
              main.accessableElements.mainMenu.style.filter =
                "drop-shadow(1px 1px 3px black)";
              break;
          }
        },
        otherMenusActive: function () {
          let otherMenus = [
              "hud-menu-shop",
              "hud-menu-settings",
              "hud-menu-party",
            ],
            visible = 0;
          otherMenus.forEach((menu) => {
            if (
              document.getElementsByClassName(menu)[0].getBoundingClientRect()
                .width > 0 ||
              document
                .getElementsByClassName("hud-chat")[0]
                .className.includes("is-focused")
            ) {
              visible++;
            }
          });
          return visible > 0 ? true : false;
        },
      },
      //getBoundingClientRect() Solves all the problems!
      controlling: {
        handleZ_Index: () => {
          main.modularFunctions.inChat() == true
            ? (main.accessableElements.mainMenu.style.zIndex = "5")
            : (main.accessableElements.mainMenu.style.zIndex = "14");
        },
        stopUpgradeMenu: () => {
          if (main.accessableElements.mainMenu.info.properties.scale().x > 0) {
            document.getElementsByClassName(
              "hud-building-overlay hud-tooltip hud-tooltip-top"
            )[0].style.display = "none";
          }
        },
      },
    },
    {
      name: "transitionMenus",
      type: "div",
      attributes: {
        className: "menu hud-building-overlay hud-tooltip hud-tooltip-top",
      },
      parent: "mainMenu",
      properties: { state: "default" },
    },
    {
      name: "menusButtonsContainer",
      type: "div",
      attributes: {
        innerHTML: `
        <button class="activatespectateMenu"><span></span></button>
              <button class="activatePetMenu"><span></span></button>`,
        className: "activateMenuButtonsContainer",
      },
      parent: "mainMenu",
      properties: {
        active: false,
        activated: function (changeActiveState) {
          main.accessableElements.menusButtonsContainer.style.left = "100%";
          main.accessableElements.menusButtonsContainer.style.opacity = "1";
          main.accessableElements.menusButtonsContainer.style.pointerEvents =
            "all";
          main.accessableElements.menusButtonsContainer.style.zIndex = "2";
          if (!changeActiveState) {
            this.active = true;
          }
        },
        deactivated: function (changeActiveState) {
          main.accessableElements.menusButtonsContainer.style.opacity = "0";
          var containerClient =
              main.accessableElements.menusButtonsContainer.getBoundingClientRect(),
            mainMenuClient =
              main.accessableElements.mainMenu.getBoundingClientRect();
          main.accessableElements.menusButtonsContainer.style.left = `${(
            100 -
            ((mainMenuClient.width -
              (mainMenuClient.width - containerClient.width)) /
              mainMenuClient.width) *
              100
          ).toFixed(2)}%`;
          main.accessableElements.menusButtonsContainer.style.pointerEvents =
            "none";
          main.accessableElements.menusButtonsContainer.style.zIndex = "-1";
          if (!changeActiveState) {
            this.active = false;
          }
        },
        getVisibleButtons: () => {
          let visibleChildren = 0;
          main.accessableElements.menusButtonsContainer
            .querySelectorAll("button")
            .forEach((button) => {
              button.getBoundingClientRect().width > 0
                ? visibleChildren++
                : null;
            });
          return visibleChildren;
        },
      },
    },
    //👇I am tired and now I won't remove this
    {
      name: "tooltipPlayerHealthP",
      type: "p",
      attributes: {
        className: "playerHealth",
      },
      parent: function () {
        return document
          .getElementsByClassName("mainMenu")[0]
          .getElementsByClassName("hud-tooltip-health")[0];
      },
    },
    //This button was called switchButton before
    {
      name: "arrowButton",
      type: "button",
      attributes: {
        className: "arrowButton",
        innerHTML: `
          <p>></p>
          `,
      },
      parent: "mainMenu",
      properties: {
        activated: () => {
          if (
            main.accessableElements.transitionMenus.info.properties.state ==
            "default"
          ) {
            main.accessableElements.menusButtonsContainer.info.properties.activated();
            main.accessableElements.arrowButton.getElementsByTagName(
              "p"
            )[0].style.transform = "translate(-50%,-50%) rotateY(180deg)";
          }
        },
        deactivated: () => {
          if (
            main.accessableElements.transitionMenus.info.properties.state ==
            "default"
          ) {
            main.accessableElements.menusButtonsContainer.info.properties.deactivated();
            main.accessableElements.arrowButton.getElementsByTagName(
              "p"
            )[0].style.transform = "translate(-50%,-50%) rotateX(0deg)";
          } else {
            main.properties.currentMenu = "mainMenu";
            main.accessableElements.arrowButton.getElementsByTagName(
              "p"
            )[0].style.transform = "translate(-50%,-50%) rotateX(0deg)";
            main.accessableElements.arrowButton.style.left = "87.5%";
            main.accessableElements.mainMenu.getElementsByClassName(
              "hud-building-overlay hud-tooltip hud-tooltip-top info-container"
            )[0].style.opacity = "1";
            main.accessableElements.mainMenu.getElementsByClassName(
              "hud-building-overlay hud-tooltip hud-tooltip-top info-container"
            )[0].style.pointerEvents = "all";
            main.accessableElements.transitionMenus.style.pointerEvents =
              "none";
            main.accessableElements.transitionMenus.style.left = "-50%";
            main.accessableElements.transitionMenus.style.opacity = "0";
            main.accessableElements.transitionMenus.info.properties.state =
              "default";
            main.accessableElements.menusButtonsContainer.info.properties.deactivated();
          }
        },
      },
    },
    {
      name: "spectatingText",
      type: "span",
      attributes: {
        className: "spectatemenu-spectating",
        innerText: "Spectating...",
      },
      parent: "mainMenu",
    },
    {
      name: "notificationsContainer",
      type: "div",
      attributes: {
        className: "notificationsContainer",
      },
      parent: document.getElementsByClassName("hud")[0],
    },
    {
      name: "control",
      type: "li",
      attributes: {
        innerHTML:
          "Better Player Info Menu: <strong>Alt + Hover A Player</strong>",
      },
      parent: document.getElementsByClassName("hud-settings-controls")[0],
    },
  ],
  cursor: {
    client: {
      x: 0,
      y: 0,
      target: document.body,
    },
  },
  accessableMenus: {},
  availableMenus: [
    {
      id: "petMenu",
      HTML: `
      <div class="hud-tooltip-building" style="transition: transform 0.3s">
    <h2 class="pet-Name">Undefined</h2>
    <h3 style="position: relative; left: 0px">
      Uid: <span class="hud-building-tier pet-Uid">000000000</span>
    </h3>
    <ul class="healthbars-container" style="left: 60%; top: -38%">
      <li class="hud-tooltip-health" style="position: relative;">
        <span
          class="hud-tooltip-health-bar"
          style="
            width: 100%;
            transition: all 0.2s;
            background: rgb(71, 149, 13);
          "
        ></span>
      </li>
    </ul>
    <div class="hud-tooltip-body">
      <div class="hud-building-stats">
        <button class="partyBtn" style="display: none">Join</button>
        <div class="hud-stats-current hud-stats-values">
          <p>
            Health: <strong class="hud-stats-current pet-Health">Null</strong>
          </p>
          <p>
            Level/Tier:
            <strong class="hud-stats-current pet-Level/Tier">Null</strong>
          </p>
          <p>
            Experience: <strong class="hud-stats-current pet-Exp">Null</strong>
          </p>
        </div>
        <div class="hud-stats-next hud-stats-values">
          <p style="display: none">
            Party: <strong class="hud-stats-next party-Name">Null</strong>
          </p>
        </div>
      </div>
      <p class="hud-building-actions" style="display: block">
        <span class="hud-building-dual-btn" style="display: none" <="" span="">
        </span>
      </p>
    </div>
  </div>
  <div class="petNotFound">
    <h2 align="center" style="margin-top: 15%; color: #b3353c">
      Pet not found!
    </h2>
    <p
      class="reasons"
      style="
        position: relative;
        color: #b3353c;
        font-weight: bold;
        margin-top: 0%;
        transition: all 0.3s;
      "
      align="center"
    >
      Reasons:
    </p>
    <h3
      align="center"
      style="
        position: relative;
        color: #b3353c;
        font-weight: bold;
        margin-top: -2%;
        transition: all 0.3s;
      "
    >
      Waiting for the pet... <i class="fas fa-circle-notch spinner"></i>
    </h3>
  </div>

    `,
      activatedOnce: false,
      whenActive: () => {
        let petNotFound =
            main.accessableElements.transitionMenus.getElementsByClassName(
              "petNotFound"
            )[0],
          transitionMenus = main.accessableElements.transitionMenus;
        if (!main.availableMenus[0].activatedOnce) {
          let i = 0,
            reasonsArray = [
              "Pet is dead,",
              "He is out of your screen,",
              "Or the player doesn't have one yet.",
            ];
          setInterval(() => {
            let reasons =
              main.accessableElements.transitionMenus.getElementsByClassName(
                "reasons"
              )[0];
            if (reasons) {
              i < reasonsArray.length == false ? (i = 0) : (i = i);
              if (i < reasonsArray.length) {
                reasons.style.opacity = "0";
                setTimeout(() => {
                  reasons.style.opacity = "1";
                  reasons.innerText = "Reasons: " + reasonsArray[i];
                  i++;
                }, 300);
              }
            }
          }, 3000);
          main.availableMenus[0].activatedOnce = true;
        }
        if (
          game.world.entities[main.properties.activePlayerUid] !== undefined &&
          main.properties.activePlayerUid !== undefined
        ) {
          if (
            game.world.entities[
              game.world.entities[main.properties.activePlayerUid].targetTick
                .petUid
            ] !== undefined
          ) {
            if (
              game.world.entities[
                game.world.entities[main.properties.activePlayerUid].targetTick
                  .petUid
              ].isInViewport() == true
            ) {
              var pet =
                game.world.entities[
                  game.world.entities[main.properties.activePlayerUid]
                    .targetTick.petUid
                ];
              petNotFound.style.opacity = "0";
              petNotFound.style.pointerEvents = "none";
              transitionMenus.getElementsByClassName(
                "hud-tooltip-building"
              )[0].style.transform = "scale(1,1)";
              transitionMenus.getElementsByClassName("pet-Name")[0].innerText =
                pet.targetTick.model;
              transitionMenus.getElementsByClassName("pet-Uid")[0].innerText =
                pet.targetTick.uid;
              transitionMenus.getElementsByClassName(
                "pet-Health"
              )[0].innerText = pet.targetTick.health.toFixed(1);
              transitionMenus.getElementsByClassName(
                "pet-Level/Tier"
              )[0].innerText =
                pet.currentModel.experienceBar.level +
                "/" +
                pet.targetTick.tier;
              transitionMenus.getElementsByClassName("pet-Exp")[0].innerText =
                pet.targetTick.experience;
              transitionMenus.getElementsByClassName(
                "hud-tooltip-health-bar"
              )[0].style.width =
                100 -
                ((pet.targetTick.maxHealth - pet.targetTick.health) /
                  pet.targetTick.maxHealth) *
                  100 +
                "%";
            }
          } else {
            if (main.properties.activePlayerUid !== undefined) {
              if (
                game.world.entities[
                  game.world.entities[main.properties.activePlayerUid]
                    .targetTick.petUid
                ] == undefined
              ) {
                transitionMenus.getElementsByClassName(
                  "hud-tooltip-building"
                )[0].style.transform = "scale(0,0)";
                petNotFound.style.pointerEvents = "all";
                petNotFound.style.opacity = "1";
              }
            }
          }
        }
      },
    },
    {
      id: "spectateMenu",
      HTML: `<button class="spectatemenu-button" style="margin-top: 5px;"><span class="spectatemenu-icon"><i></i></span><span class="spectatemenu-name">Unset</span><span class="spectatemenu-rank">Leader</span></button><button class="spectatemenu-button"><span class="spectatemenu-icon"><i></i></span><span class="spectatemenu-name">Unset</span><span class="spectatemenu-rank">Leader</span></button><button class="spectatemenu-button"><span class="spectatemenu-icon"><i></i></span><span class="spectatemenu-name">Unset</span><span class="spectatemenu-rank">Leader</span></button><button class="spectatemenu-button"><span class="spectatemenu-icon"><i></i></span><span class="spectatemenu-name">Unset</span><span class="spectatemenu-rank">Leader</span></button><div class="spectatemenu-background"></div>`,
      getAllMembers: function () {
        if (
          game.network.connected &&
          game.world.inWorld &&
          game.ui?.playerTick
        ) {
          let members = game.ui.playerPartyMembers,
            countedMembers = 0;
          members.forEach((member) => {
            if (
              member.playerUid !== main.properties.activePlayerUid &&
              member.playerUid !== game.ui.playerTick.uid
            ) {
              countedMembers++;
            }
          });
          return countedMembers;
        }
      },
      FPS: 1,
      lastFrameTime: 0,
      timeSinceLastFrame: 0,
      whenActive: function (timestamp) {
        this.timeSinceLastFrame = timestamp - this.lastFrameTime;
        if (this.timeSinceLastFrame >= 1000 / this.FPS) {
          this.lastFrameTime = timestamp;
          let allMembers = game.ui.playerPartyMembers,
            activeIndex = 0;
          allMembers.forEach((member, index) => {
            member.rank =
              index == 0
                ? "Leader"
                : index == 1
                ? "Co-Leader"
                : index == 2
                ? "Member"
                : "Co-Member";
          });
          Object.keys(main.accessableElements.transitionMenus.children).forEach(
            (element, index) => {
              let currentElement =
                main.accessableElements.transitionMenus.children[element];
              currentElement.onmousedown = (event) => {
                  event.preventDefault();
                  event.stopPropagation();
                let id = event.target.id || event.target.parentNode.id,
                  allMembers = game.ui.playerPartyMembers;
                if (id) {
                  let currentPlayer = allMembers.find(
                    (member) => member.playerUid == id
                  );
                  if (currentPlayer) {
                    main.accessableElements.mainMenu.getElementsByClassName(
                      "hud-building-overlay hud-tooltip hud-tooltip-top info-container"
                    )[0].style.opacity = "1";
                    main.accessableElements.mainMenu.getElementsByClassName(
                      "hud-building-overlay hud-tooltip hud-tooltip-top info-container"
                    )[0].style.pointerEvents = "all";
                    main.accessableElements.transitionMenus.style.pointerEvents =
                      "none";
                    main.accessableElements.transitionMenus.style.left = "-50%";
                    main.accessableElements.transitionMenus.style.opacity = "0";
                    main.accessableElements.transitionMenus.info.properties.state =
                      "default";
                    main.properties.activePlayerUid = currentPlayer.playerUid;
                    main.properties.isSpectating = true;
                  }
                }
              };
              if (currentElement.nodeName.toUpperCase() == "BUTTON") {
                if (
                  index < allMembers.length &&
                  allMembers[index].playerUid !==
                    main.properties.activePlayerUid &&
                  allMembers[index].playerUid !== game.ui.playerTick.uid
                ) {
                  let namePara =
                      currentElement.getElementsByClassName(
                        "spectatemenu-name"
                      )[0],
                    rankPara =
                      currentElement.getElementsByClassName(
                        "spectatemenu-rank"
                      )[0],
                    iconSpan =
                      currentElement.getElementsByClassName(
                        "spectatemenu-icon"
                      )[0],
                    playerName = allMembers[index].displayName;
                  rankPara.innerText = allMembers[index].rank ?? "Unknown_Rank";
                  iconSpan.style.background =
                    allMembers[index].rank == "Leader"
                      ? "rgba(155, 89, 182, 0.25)"
                      : allMembers[index].rank == "Co-Leader"
                      ? "rgba(241, 196, 15, 0.25)"
                      : allMembers[index].rank == "Member"
                      ? "rgba(46, 204, 113, 0.25)"
                      : "rgba(243, 156, 18, 0.25)";
                  iconSpan.getElementsByTagName("i")[0].className =
                    allMembers[index].rank == "Leader" ||
                    allMembers[index].rank == "Co-Leader"
                      ? "fas fa-crown"
                      : "fas fa-user";
                  iconSpan.getElementsByTagName("i")[0].style.color =
                    allMembers[index].rank == "Leader"
                      ? "rgb(155, 89, 182)"
                      : allMembers[index].rank == "Co-Leader"
                      ? "rgb(241,196,15)"
                      : allMembers[index].rank == "Member"
                      ? "rgb(46,204,113)"
                      : "rgb(243, 156, 18)";
                  currentElement.id = allMembers[index].playerUid;
                  if (this.getAllMembers() == 1) {
                    namePara.innerText =
                      playerName.length > 9
                        ? playerName.slice(0, 9) + "..."
                        : playerName;
                  } else if (this.getAllMembers() == 2) {
                    namePara.innerText =
                      playerName.length > 13
                        ? playerName.slice(0, 13) + "..."
                        : playerName;
                  } else if (this.getAllMembers() == 3) {
                    namePara.innerText =
                      playerName.length > 16
                        ? playerName.slice(0, 16) + "..."
                        : playerName;
                  }
                  activeIndex++;
                  if (activeIndex == 1) {
                    currentElement.style.position = "relative";
                    setTimeout(() => {
                      currentElement.style.top = "0%";
                      currentElement.style.opacity = "1";
                    }, 500);
                    currentElement.style.marginTop = "6px";
                  } else {
                    currentElement.style.position = "relative";
                    setTimeout(() => {
                      currentElement.style.top = "0%";
                      currentElement.style.opacity = "1";
                    }, 500);
                    currentElement.style.marginTop = "0px";
                  }
                } else {
                  //You don't know how hard these transitions are, And how long they took me to be figured out
                  currentElement.style.opacity = "0";
                  currentElement.style.top = "100%";
                  setTimeout(() => {
                    currentElement.style.position = "absolute";
                  }, 500);
                }
              }
            }
          );
        }
      },
      deactivated: function () {
        let spectateMenu = main.accessableMenus.spectateMenu;
        main.properties.activePlayerUid = game.ui.playerTick.uid;
        main.accessableElements.mainMenu.getElementsByClassName(
          "hud-building-overlay hud-tooltip hud-tooltip-top info-container"
        )[0].style.opacity = "0";
        main.accessableElements.mainMenu.getElementsByClassName(
          "hud-building-overlay hud-tooltip hud-tooltip-top info-container"
        )[0].style.pointerEvents = "all";
        main.accessableElements.transitionMenus.style.left = "50%";
        main.accessableElements.transitionMenus.style.opacity = "1";
        main.accessableElements.arrowButton.style.left = "-4%";
        main.accessableElements.menusButtonsContainer.info.properties.deactivated(
          true
        );
        main.properties.isSpectating = false;
        main.accessableElements.transitionMenus.innerHTML = spectateMenu.HTML;
        main.accessableElements.transitionMenus.info.properties.state =
          spectateMenu.id;
      },
    },
  ],
  icons: [
    {
      for: "petMenu",
      check: function () {
        if (!main.properties.global.pet) return false;
        else if (
          main.properties.global.pet &&
          main.properties.global.pet.targetTick.model
            .toUpperCase()
            .includes("CARL")
        )
          //👇Got the idea(Literally copied) to use discord as a hosting site for icons from the Xeraphinite dev: rdm, god of simping :D
          return "https://cdn.discordapp.com/attachments/853498284484460574/940110415755608084/Carl-Weapon.png";
        else if (
          main.properties.global.pet &&
          main.properties.global.pet.targetTick.model
            .toUpperCase()
            .includes("MINER")
        )
          return "https://cdn.discordapp.com/attachments/853498284484460574/940114196291539024/pet-miner-t3-weapon.png";
      },
    },
    {
      for: "spectateMenu",
      check: function () {
        if (main.accessableMenus.spectateMenu.getAllMembers() == 0)
          return false;
        else if (main.accessableMenus.spectateMenu.getAllMembers() == 1)
          return "https://cdn.discordapp.com/attachments/853498284484460574/940455096528039956/Single_player_icon.png";
        else if (main.accessableMenus.spectateMenu.getAllMembers() == 2)
          return "https://cdn.discordapp.com/attachments/853498284484460574/940454046089744404/Party-icon_-_Copy.png";
        else if (main.accessableMenus.spectateMenu.getAllMembers() == 3)
          return "https://cdn.discordapp.com/attachments/853498284484460574/940454001869205544/Party-icon.png";
      },
      do: (element) => {
        let spanElement = element.getElementsByTagName("span")[0];
        spanElement.style.transform = "rotate(0)";
        spanElement.style.top = "20%";
        if (main.accessableMenus.spectateMenu.getAllMembers() == 1) {
          spanElement.style.backgroundSize = "14px";
          spanElement.style.left = "25%";
        } else if (main.accessableMenus.spectateMenu.getAllMembers() == 2) {
          spanElement.style.backgroundSize = "17px";
          spanElement.style.left = "20%";
        } else if (main.accessableMenus.spectateMenu.getAllMembers() == 3) {
          spanElement.style.backgroundSize = "20px";
          spanElement.style.left = "20%";
        }
      },
    },
  ],
};
main.modularFunctions.arrayToHTML(main.elements);
//👇What. IS. THE. DAMNNN. NEED. OF. THIS!!!!!!
window.customNotification = class customNotification {
  constructor(text, time, displayAfter) {
    this.text = text;
    this.time = time ?? 5000;
    this.displayAfter = displayAfter ?? 500;
    this.isLooked = false;
    let element = document.createElement("div");
    element.className = "notification-main";
    element.innerHTML = `
<h4 class="notification-label">Better player info</h4>
<div class="notification-background">
<i class="fas fa-check notification-Icon"></i>
<div class="notification-errors">
<span> 0</span>
</div>
<span class="notification-text">Everything looks good!</span>
</div>
</div>`;
    element.getElementsByTagName("i")[0].addEventListener("mousedown", (e) => {
      e.preventDefault();
      e.stopPropagation();
      element.style.left = "-100%";
      setTimeout(() => {
        element.style.minHeight = "0px";
        element.style.height = "0.1%";
        setTimeout(() => {
          element.remove();
          this.isLooked = true;
        }, this.displayAfter);
      }, 750);
    });
    main.accessableElements.notificationsContainer.append(element);
    element.getElementsByClassName("notification-text")[0].innerText =
      this.text;
    main
      ? main.properties.notificationsHandler.queuedNotifications.push(this)
      : betterPlayerInfo.properties.notificationsHandler.queuedNotifications.push(
          this
        );
    if (main.properties.showNotifications) {
      setTimeout(() => {
        element.style.left = "0%";
      }, this.displayAfter);
    }
    setTimeout(() => {
      //This transition also took me long time
      element.style.left = "-100%";
      setTimeout(() => {
        element.style.minHeight = "0px";
        element.style.height = "0.1%";
        setTimeout(() => {
          element.remove();
          this.isLooked = true;
        }, this.displayAfter);
      }, 750);
    }, this.time + this.displayAfter);
  }
};
window.betterPlayerInfo = main;
window.addEventListener("mousedown", (client) => {
  main.cursor.client = client;
});
main.availableMenus.forEach((menu) => {
  main.accessableMenus[menu.id] = menu;
});
main.accessableElements.menusButtonsContainer.style.top = `${
  98 -
  (main.accessableElements.menusButtonsContainer.childElementCount - 1) * 10
}%`;
function handleMenuActivation() {
  main.accessableElements.menusButtonsContainer.addEventListener(
    "mousedown",
    (event) => {
      event.preventDefault();
      event.stopPropagation();
      if (event.target.nodeName == "BUTTON") {
        main.availableMenus.forEach((menu) => {
          if (
            event.target.className.toUpperCase().includes(menu.id.toUpperCase())
          ) {
            main.accessableElements.mainMenu.getElementsByClassName(
              "hud-building-overlay hud-tooltip hud-tooltip-top info-container"
            )[0].style.opacity = "0";
            main.accessableElements.mainMenu.getElementsByClassName(
              "hud-building-overlay hud-tooltip hud-tooltip-top info-container"
            )[0].style.pointerEvents = "all";
            main.accessableElements.transitionMenus.info.properties.state =
              menu.id;
            main.accessableElements.transitionMenus.innerHTML = menu.HTML;
            main.accessableElements.transitionMenus.style.opacity = "1";
            main.accessableElements.arrowButton.style.left = "-4%";
            main.accessableElements.menusButtonsContainer.info.properties.deactivated(
              true
            );
            main.accessableElements.transitionMenus.style.left = "50%";
            main.properties.currentMenu = menu.id;
          }
        });
      }
    }
  );
}
handleMenuActivation();
function handleSpectateButtonStyle() {
  let root = document.querySelector(":root");
  if (main.accessableMenus.spectateMenu.getAllMembers() == 1) {
    root.style.setProperty("--spectatemenu-buttons-height", "81%");
    root.style.setProperty("--spectatemenu-buttons-icon-width", "100%");
    root.style.setProperty("--spectatemenu-buttons-icon-height", "40%");
    root.style.setProperty("--spectatemenu-buttons-name-fontSize", "41px");
    root.style.setProperty("--spectatemenu-buttons-name-top", "45%");
    main.accessableElements.transitionMenus
      .querySelectorAll(".spectatemenu-name")
      .forEach((name) => {
        name.style.left = "50%";
        name.style.transform = "translateX(-50%)";
        name.style.textAlign = "";
      });
    main.accessableElements.transitionMenus
      .querySelectorAll(".spectatemenu-rank")
      .forEach((rank) => {
        rank.style.left = "50%";
        rank.style.transform = "translateX(-50%)";
        rank.style.bottom = "1%";
      });
    root.style.setProperty("--spectatemenu-buttons-rank-fontSize", "25px");
    main.accessableElements.transitionMenus
      .querySelectorAll(".spectatemenu-icon")
      .forEach((icon) => {
        icon.getElementsByTagName("i")[0].style.fontSize = "32px";
      });
  } else if (main.accessableMenus.spectateMenu.getAllMembers() == 2) {
    root.style.setProperty("--spectatemenu-buttons-height", "38.5%");
    root.style.setProperty("--spectatemenu-buttons-icon-width", "15%");
    root.style.setProperty("--spectatemenu-buttons-icon-height", "100%");
    root.style.setProperty("--spectatemenu-buttons-name-fontSize", "25px");
    root.style.setProperty("--spectatemenu-buttons-name-top", "10%");
    root.style.setProperty("--spectatemenu-buttons-name-left", "17%");
    main.accessableElements.transitionMenus
      .querySelectorAll(".spectatemenu-name")
      .forEach((name) => {
        name.style.textAlign = "left";
        name.style.left = "18%";
        name.style.transform = "translateX(0)";
      });
    main.accessableElements.transitionMenus
      .querySelectorAll(".spectatemenu-rank")
      .forEach((rank) => {
        rank.style.left = "18%";
        rank.style.bottom = "1%";
        rank.style.transform = "translateX(0)";
      });
    root.style.setProperty("--spectatemenu-buttons-rank-fontSize", "23px");
    main.accessableElements.transitionMenus
      .querySelectorAll(".spectatemenu-icon")
      .forEach((icon) => {
        icon.getElementsByTagName("i")[0].style.fontSize = "22px";
      });
  } else if (main.accessableMenus.spectateMenu.getAllMembers() == 3) {
    root.style.setProperty("--spectatemenu-buttons-height", "24%");
    root.style.setProperty("--spectatemenu-buttons-icon-width", "10%");
    root.style.setProperty("--spectatemenu-buttons-icon-height", "100%");
    root.style.setProperty("--spectatemenu-buttons-name-fontSize", "17px");
    root.style.setProperty("--spectatemenu-buttons-name-top", "10%");
    main.accessableElements.transitionMenus
      .querySelectorAll(".spectatemenu-name")
      .forEach((name) => {
        name.style.textAlign = "left";
        name.style.transform = "translateX(0)";
        name.style.left = "12%";
      });
    main.accessableElements.transitionMenus
      .querySelectorAll(".spectatemenu-rank")
      .forEach((rank) => {
        rank.style.left = "12%";
        rank.style.bottom = "1%";
        rank.style.transform = "translateX(0)";
      });
    root.style.setProperty("--spectatemenu-buttons-rank-fontSize", "15px");
    main.accessableElements.transitionMenus
      .querySelectorAll(".spectatemenu-icon")
      .forEach((icon) => {
        icon.getElementsByTagName("i")[0].style.fontSize = "16px";
      });
  }
}
//handlePlayerTracking, So I could come to your house and beat the heck out of you, If you dare copy this script, Just kidding
function handlePlayerTracking(e) {
  if (
    game.network.connected &&
    game.world.inWorld &&
    main.properties.allowRetrack
  ) {
    main.properties.allowRetrack = false;
    if (
      main.accessableElements.transitionMenus.info.properties.state == "default"
    ) {
      document.getElementsByClassName(
        "hud-building-overlay hud-tooltip hud-tooltip-top info-container"
      )[0].style.opacity = "1";
      main.accessableElements.mainMenu.getElementsByClassName(
        "hud-building-overlay hud-tooltip hud-tooltip-top info-container"
      )[0].style.pointerEvents = "all";
    }
    main.properties.playerTracker.mainPlayer.mousePosition =
      game.ui.mousePosition;
    main.properties.playerTracker.mainPlayer.mousePositionX =
      main.properties.playerTracker.mainPlayer.mousePosition.x;
    main.properties.playerTracker.mainPlayer.mousePositionY =
      main.properties.playerTracker.mainPlayer.mousePosition.y;
    main.properties.playerTracker.mainPlayer.convertedMousePositionX =
      game.renderer.screenToWorld(
        main.properties.playerTracker.mainPlayer.mousePositionX,
        main.properties.playerTracker.mainPlayer.mousePositionY
      ).x;
    main.properties.playerTracker.mainPlayer.convertedMousePositionY =
      game.renderer.screenToWorld(
        main.properties.playerTracker.mainPlayer.mousePositionX,
        main.properties.playerTracker.mainPlayer.mousePositionY
      ).y;
    Object.entries(game.world.entities).forEach((player) => {
      if (player[1].entityClass == "PlayerEntity") {
        main.properties.playerTracker.mainPlayer.calculatedX =
          player[1].targetTick.position.x -
          main.properties.playerTracker.mainPlayer.convertedMousePositionX;
        main.properties.playerTracker.mainPlayer.calculatedY =
          player[1].targetTick.position.y -
          main.properties.playerTracker.mainPlayer.convertedMousePositionY;
        main.properties.playerTracker.mainPlayer.distance = Math.sqrt(
          main.properties.playerTracker.mainPlayer.calculatedX *
            main.properties.playerTracker.mainPlayer.calculatedX +
            main.properties.playerTracker.mainPlayer.calculatedY *
              main.properties.playerTracker.mainPlayer.calculatedY
        );
        main.properties.playerTracker.mainPlayer.mouseDistanceFromPlayer =
          main.properties.playerTracker.mainPlayer.distance +
          player[1].currentModel.base.node.width;
        if (
          main.properties.playerTracker.mainPlayer.mouseDistanceFromPlayer <
            99 + main.properties.playerTracker.cursorSize &&
          !main.properties.isSpectating
        ) {
          if (
            main.accessableElements.transitionMenus.info.properties.state
              .toUpperCase()
              .includes("SPECTATE") &&
            main.properties.activePlayerUid !== player[1].targetTick.uid
          ) {
            main.accessableElements.arrowButton.info.properties.deactivated();
          }
          main.properties.activePlayerUid = player[1].targetTick.uid;
        }
      }
    });
    if (
      game.world.entities[main.properties.activePlayerUid] ||
      main.properties.activePlayerUid !== game.ui.playerTick.uid
    ) {
      if (game.world.entities[main.properties.activePlayerUid]) {
        main.properties.playerTracker.targetedPlayer.mousePosition =
          game.ui.mousePosition;
        main.properties.playerTracker.targetedPlayer.mousePositionX =
          main.properties.playerTracker.targetedPlayer.mousePosition.x;
        main.properties.playerTracker.targetedPlayer.mousePositionY =
          main.properties.playerTracker.targetedPlayer.mousePosition.y;
        main.properties.playerTracker.targetedPlayer.convertedMousePositionX =
          game.renderer.screenToWorld(
            main.properties.playerTracker.targetedPlayer.mousePositionX,
            main.properties.playerTracker.targetedPlayer.mousePositionY
          ).x;
        main.properties.playerTracker.targetedPlayer.convertedMousePositionY =
          game.renderer.screenToWorld(
            main.properties.playerTracker.targetedPlayer.mousePositionX,
            main.properties.playerTracker.targetedPlayer.mousePositionY
          ).y;
        main.properties.playerTracker.targetedPlayer.calculatedX =
          game.world.entities[main.properties.activePlayerUid].targetTick
            .position.x -
          main.properties.playerTracker.targetedPlayer.convertedMousePositionX;
        main.properties.playerTracker.targetedPlayer.calculatedY =
          game.world.entities[main.properties.activePlayerUid].targetTick
            .position.y -
          main.properties.playerTracker.targetedPlayer.convertedMousePositionY;
        main.properties.playerTracker.targetedPlayer.distance = Math.sqrt(
          main.properties.playerTracker.targetedPlayer.calculatedX *
            main.properties.playerTracker.targetedPlayer.calculatedX +
            main.properties.playerTracker.targetedPlayer.calculatedY *
              main.properties.playerTracker.targetedPlayer.calculatedY
        );
        main.properties.playerTracker.targetedPlayer.mouseDistanceFromPlayer =
          main.properties.playerTracker.targetedPlayer.distance + 80;
      }
      if (
        game.world.entities[main.properties.activePlayerUid] &&
        main.properties.playerTracker.targetedPlayer.mouseDistanceFromPlayer
      ) {
        main.properties.displayMainMenu = true;
        if (
          game.world.entities[main.properties.activePlayerUid] !== undefined
        ) {
          window.mainMenuX =
            game.renderer.worldToScreen(
              game.world.entities[main.properties.activePlayerUid].targetTick
                .position.x,
              game.world.entities[main.properties.activePlayerUid].targetTick
                .position.y
            ).x -
            200 +
            "px";
          window.mainMenuY =
            game.renderer.worldToScreen(
              game.world.entities[main.properties.activePlayerUid].targetTick
                .position.x,
              game.world.entities[main.properties.activePlayerUid].targetTick
                .position.y
            ).y -
            290 +
            "px";
          if (main.properties.isSpectating) {
            window.mainMenuX =
              game.renderer.worldToScreen(
                game.world.entities[game.ui.playerTick.uid].targetTick.position
                  .x,
                game.world.entities[game.ui.playerTick.uid].targetTick.position
                  .y
              ).x -
              200 +
              "px";
            window.mainMenuY =
              game.renderer.worldToScreen(
                game.world.entities[game.ui.playerTick.uid].targetTick.position
                  .x,
                game.world.entities[game.ui.playerTick.uid].targetTick.position
                  .y
              ).y -
              290 +
              "px";
          }
        }
        if (parseInt(mainMenuX) < 0) {
          main.accessableElements.mainMenu.style.left = "0px";
        } else {
          if (
            parseInt(mainMenuX) >
            window.innerWidth - main.accessableElements.mainMenu.offsetWidth
          ) {
            main.accessableElements.mainMenu.style.left =
              window.innerWidth - 360 + "px";
          } else {
            main.accessableElements.mainMenu.style.left = mainMenuX;
          }
        }
        if (parseInt(mainMenuY) < 0) {
          main.accessableElements.mainMenu.style.top = "0px";
        } else {
          if (
            parseInt(mainMenuY) >
            window.innerHeight -
              main.accessableElements.mainMenu
                .getElementsByClassName("hud-building-overlay")[0]
                .getBoundingClientRect().height
          ) {
            main.accessableElements.mainMenu.style.top =
              window.innerHeight -
              main.accessableElements.mainMenu
                .getElementsByClassName("hud-building-overlay")[0]
                .getBoundingClientRect().height +
              "px";
          } else {
            main.accessableElements.mainMenu.style.top = mainMenuY;
          }
        }
      }
      if (main.properties.displayMainMenu == true) {
        document.getElementsByClassName(
          "hud-building-overlay hud-tooltip hud-tooltip-top"
        )[0].style.display = "none";
        if (
          main.accessableElements.transitionMenus.info.properties.state ==
          "default"
        ) {
          main.accessableElements.mainMenu.style.transform =
            "scale(1) rotate(0deg)";
        }
        main.accessableElements.mainMenu.style.pointerEvents = "all";
      } else if (main.properties.displayMainMenu == false) {
        if (
          main.accessableElements.transitionMenus.info.properties.state ==
          "default"
        ) {
          main.accessableElements.mainMenu.style.transform =
            "scale(0) rotate(0deg)";
          main.accessableElements.mainMenu.style.pointerEvents = "none";
        }
      }
    }
    setTimeout(() => {
      main.properties.allowRetrack = true;
    }, main.properties.retargetAfter);
  }
}
main.accessableElements.arrowButton.addEventListener("mousedown", (e) => {
  e.preventDefault();
  e.stopPropagation();
  if (main.properties.isSpectating) {
    main.accessableMenus.spectateMenu.deactivated();
  } else if (
    main.accessableElements.menusButtonsContainer.info.properties.active ==
      false &&
    main.accessableElements.transitionMenus.info.properties.state == "default"
  ) {
    main.accessableElements.menusButtonsContainer.info.properties.activated();
    main.accessableElements.arrowButton.info.properties.activated();
  } else if (
    main.accessableElements.menusButtonsContainer.info.properties.active == true
  ) {
    main.accessableElements.arrowButton.info.properties.deactivated();
  }
});
main.accessableElements.arrowButton.addEventListener("dblclick", (e) => {
  e.preventDefault();
  e.stopPropagation();
});
function allowMouseMove(e) {
  var key = e.keyCode || e.whichKey;
  if (key == 18 && main.properties.allowMouseMove == false) {
    e.preventDefault();
    main.properties.allowMouseMove = true;
    document.addEventListener("mousemove", handlePlayerTracking);
  } else if (key == 16) {
    if (main.modularFunctions.inChat() == false) {
      main.accessableElements.mainMenu.style.transform = "scale(0)";
      main.accessableElements.mainMenu.style.pointerEvents = "none";
    }
  }
}
//rejectMouseMove just like she rejected y- Ahmm, I should shut up
function rejectMouseMove(e) {
  var key = e.keyCode || e.whichKey;
  if (key == 18 && main.properties.allowMouseMove == true) {
    e.preventDefault();
    main.properties.allowMouseMove = false;
    document.removeEventListener("mousemove", handlePlayerTracking);
  } else if (key == 16) {
    main.accessableElements.mainMenu.info.properties.closedThrough("shiftkey");
  }
}
document.addEventListener("keydown", allowMouseMove);
document.addEventListener("keyup", rejectMouseMove);
main.accessableElements.mainMenu.style.transform = "scale(0) rotate(0deg)";
(window.shieldBar =
  main.accessableElements.mainMenu.getElementsByClassName("shield-bar")[0]),
  (window.menusButtonsContainer =
    main.accessableElements.mainMenu.getElementsByClassName(
      "activateMenuButtonsContainer"
    )[0]);
window.addEventListener("mousedown", (e) => {
  main.accessableElements.mainMenu.info.properties.closedThrough("clicked");
});
//Some people say this script is overcomplicated. Pfft, why don't you say you su-, Ahmm-hmm I mean it's not that overcomplicated don't know what they found so hard
function updateInfo(timeStamp) {
  window.requestAnimationFrame(updateInfo);
  main.properties.updater.calculationProcesses.timeSinceLastFrame =
    timeStamp - main.properties.updater.calculationProcesses.lastFrameTime;
  main.properties.iconHandler.mainFunction(timeStamp);
  if (
    main.properties.updater.calculationProcesses.timeSinceLastFrame >=
    1000 / main.properties.updater.clientProcesses.FPSlimit
  ) {
    main.properties.notificationsHandler.updater.main(timeStamp);
    if (main.properties.displayMainMenu) {
      document.getElementById("hud-popup-overlay").style.zIndex = "15";
    } else {
      document.getElementById("hud-popup-overlay").style.zIndex = "10";
    }
    if (main.properties.isSpectating) {
      main.accessableElements.spectatingText.style.opacity = "1";
      main.accessableElements.spectatingText.style.zIndex = "1";
    } else {
      main.accessableElements.spectatingText.style.opacity = "0";
      main.accessableElements.spectatingText.style.zIndex = "-1";
    }
    main.properties.updater.calculationProcesses.lastFrameTime = timeStamp;
    if (
      new Date() - main.properties.updater.calculationProcesses.storedFPStime >=
      1000
    ) {
      main.properties.updater.calculationProcesses.storedFPStime = new Date();
      main.properties.updater.clientProcesses.currentFPS =
        main.properties.updater.calculationProcesses.FPSstored = 0;
    } else {
      main.properties.updater.calculationProcesses.FPSstored++;
    }
    if (game.network.connected && game.world.inWorld) {
      Object.entries(game.world.entities).forEach((player) => {
        let current = player[1];
        if (
          main.properties.activePlayerUid !== undefined &&
          main.properties.displayMainMenu == true
        ) {
          if (current.targetTick.uid == main.properties.activePlayerUid) {
            if (
              main.accessableElements.mainMenu.info.properties.scale().x > 0
            ) {
              var playerName =
                main.accessableElements.mainMenu.getElementsByClassName(
                  "player-Name"
                )[0];
              let maxLength = 11,
                mainMenu = main.accessableElements.mainMenu;
              playerName.innerText = player[1].targetTick.name;
              playerName.innerText.length > maxLength
                ? (playerName.innerText =
                    playerName.innerText.substr(0, maxLength) + "...")
                : (playerName.innerText = current.targetTick.name);
              playerName.style.height = "31px";
              mainMenu.getElementsByClassName("player-Uid")[0].innerText =
                current.targetTick.uid;
              mainMenu.getElementsByClassName("player-Wood")[0].innerText =
                current.targetTick.wood.toFixed(2);
              mainMenu.getElementsByClassName("player-Stone")[0].innerText =
                current.targetTick.stone.toFixed(2);
              mainMenu.getElementsByClassName("player-Gold")[0].innerText =
                current.targetTick.gold.toFixed(2);
              mainMenu.getElementsByClassName("player-Score")[0].innerText =
                current.targetTick.score.toFixed(2);
              mainMenu.getElementsByClassName("player-Tokens")[0].innerText =
                current.targetTick.token.toFixed(2);
                // if(current.targetTick.zombieShieldMaxHealth <= 0){
              mainMenu.getElementsByClassName("player-Health")[0].innerText =
                current.targetTick.health.toFixed(2);
                // }
                //else{
                // mainMenu.getElementsByClassName("player-Health")[0].innerText =
                // `${current.targetTick.health.toFixed(2)}/${current.targetTick.zombieShieldHealth}`;
                // };
              mainMenu.getElementsByClassName(
                "hud-tooltip-health-bar"
              )[0].style.width = `${
                100 -
                ((current.targetTick.maxHealth - current.targetTick.health) /
                  current.targetTick.maxHealth) *
                  100
              }%`;
              if (current.targetTick.zombieShieldMaxHealth > 0) {
                mainMenu.getElementsByClassName(
                  "healthbars-container"
                )[0].style.top = "-26%";
                mainMenu.getElementsByClassName("shield-bar")[0].style.display =
                  "block";
                mainMenu
                  .getElementsByClassName("shield-bar")[0]
                  .getElementsByTagName("span")[0].style.width = `${
                  100 -
                  ((current.targetTick.zombieShieldMaxHealth -
                    current.targetTick.zombieShieldHealth) /
                    current.targetTick.zombieShieldMaxHealth) *
                    100
                }%`;
                mainMenu
                  .getElementsByClassName("shield-bar")[0]
                  .getElementsByTagName("span")[0].style.display = "block";
              } else {
                mainMenu.getElementsByClassName(
                  "healthbars-container"
                )[0].style.top = "-24%";
                mainMenu.getElementsByClassName("shield-bar")[0].style.display =
                  "none";
              }
            }
          }
        }
      });
    }
    main.availableMenus.forEach((menu) => {
      if (
        menu.id.toUpperCase() ==
        main.accessableElements.transitionMenus.info.properties.state.toUpperCase()
      ) {
        menu.whenActive?.(timeStamp);
      }
    });
    if (
      game.world.inWorld &&
      game.network.connected &&
      game.ui.playerTick.health <= 0 &&
      main.properties.displayMainMenu
    ) {
      main.accessableElements.mainMenu.info.properties.closedThrough(
        "shiftkey"
      );
    }
    main.accessableElements.mainMenu.info.controlling.stopUpgradeMenu();
    main.accessableElements.mainMenu.info.controlling.handleZ_Index();
  }
}
updateInfo(0);
main.modularFunctions.onEnteringGame();
//You can call this script dumb and waste of time, But who doesn't like cool stuff :).
//And feel free to use this in other projects Like a script that has different menus and it should have cool transitions! Just give credit or I'll be sad :(.

QingJ © 2025

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