Greasy Fork 支持简体中文。

Shell Shockers Hide FPS

Hide FPS and uncap it (FAKE)

目前為 2024-12-24 提交的版本,檢視 最新版本

  1. // ==UserScript==
  2. // @name Shell Shockers Hide FPS
  3. // @license GPL-3.0
  4. // @version 1.3.1
  5. // @author wish?
  6. // @grant none
  7. // @run-at document-start
  8. // @require https://cdnjs.cloudflare.com/ajax/libs/crypto-js/4.1.1/crypto-js.min.js
  9. // @require https://cdn.jsdelivr.net/npm/tweakpane@3.1.10/dist/tweakpane.min.js
  10. // @require https://cdn.jsdelivr.net/npm/@tweakpane/plugin-essentials@0.1.8/dist/tweakpane-plugin-essentials.min.js
  11. // @require https://cdnjs.cloudflare.com/ajax/libs/jszip/3.7.1/jszip.min.js
  12. // @description Hide FPS and uncap it (FAKE)
  13. //
  14. //
  15. // @match *://eggshooter.best/*
  16. // @match *://*.shellshock.io/*
  17. // @match *://*.algebra.best/*
  18. // @match *://*.algebra.vip/*
  19. // @match *://*.biologyclass.club/*
  20. // @match *://*.deadlyegg.com/*
  21. // @match *://*.deathegg.world/*
  22. // @match *://*.eggboy.club/*
  23. // @match *://*.eggboy.xyz/*
  24. // @match *://*.eggcombat.com/*
  25. // @match *://*.egg.dance/*
  26. // @match *://*.eggfacts.fun/*
  27. // @match *://*.egghead.institute/*
  28. // @match *://*.eggisthenewblack.com/*
  29. // @match *://*.eggsarecool.com/*
  30. // @match *://*.geometry.best/*
  31. // @match *://*.geometry.monster/*
  32. // @match *://*.geometry.pw/*
  33. // @match *://*.geometry.report/*
  34. // @match *://*.hardboiled.life/*
  35. // @match *://*.hardshell.life/*
  36. // @match *://*.humanorganising.org/*
  37. // @match *://*.mathactivity.xyz/*
  38. // @match *://*.mathactivity.club/*
  39. // @match *://*.mathdrills.info/*
  40. // @match *://*.mathdrills.life/*
  41. // @match *://*.mathfun.rocks/*
  42. // @match *://*.mathgames.world/*
  43. // @match *://*.math.international/*
  44. // @match *://*.mathlete.fun/*
  45. // @match *://*.mathlete.pro/*
  46. // @match *://*.overeasy.club/*
  47. // @match *://*.risenegg.com/*
  48. // @match *://*.scrambled.tech/*
  49. // @match *://*.scrambled.today/*
  50. // @match *://*.scrambled.us/*
  51. // @match *://*.scrambled.world/*
  52. // @match *://*.shellshockers.club/*
  53. // @match *://*.shellshockers.life/*
  54. // @match *://*.shellshockers.site/*
  55. // @match *://*.shellshockers.us/*
  56. // @match *://*.shellshockers.world/*
  57. // @match *://*.shellshockers.xyz/*
  58. // @match *://*.shellsocks.com/*
  59. // @match *://*.softboiled.club/*
  60. // @match *://*.urbanegger.com/*
  61. // @match *://*.violentegg.club/*
  62. // @match *://*.violentegg.fun/*
  63. // @match *://*.yolk.best/*
  64. // @match *://*.yolk.life/*
  65. // @match *://*.yolk.rocks/*
  66. // @match *://*.yolk.tech/*
  67. // @match *://*.yolk.quest/*
  68. // @match *://*.yolk.today/*
  69. // @match *://*.zygote.cafe/*
  70. // @match *://*.shellshockers.best/*
  71. // @match *://*.eggboy.me/*
  72. // @namespace https://greasyfork.org/users/1361048
  73. // ==/UserScript==
  74. (function () {
  75. let originalReplace = String.prototype.replace;
  76. String.prototype.originalReplace = function () {
  77. return originalReplace.apply(this, arguments);
  78. };
  79. const originalXHROpen = XMLHttpRequest.prototype.open;
  80. const originalXHRGetResponse = Object.getOwnPropertyDescriptor(XMLHttpRequest.prototype, "response");
  81. let shellshockjs;
  82. XMLHttpRequest.prototype.open = function (...args) {
  83. const url = args[1];
  84. if (url && url.includes("js/shellshock.js")) {
  85. shellshockjs = this;
  86. }
  87. originalXHROpen.apply(this, args);
  88. };
  89. Object.defineProperty(XMLHttpRequest.prototype, "response", {
  90. get: function () {
  91. if (this === shellshockjs) {
  92. return applyLibertyMutual(originalXHRGetResponse.get.call(this));
  93. }
  94. return originalXHRGetResponse.get.call(this);
  95. },
  96. });
  97. //VAR STUFF
  98. let F = [];
  99. let H = {};
  100. let functionNames = [];
  101. let tp = {
  102. hideFPS: {
  103. hide: JSON.parse(localStorage.getItem('tp-hideFPS')) || false,
  104. min: JSON.parse(localStorage.getItem('tp-minFPS')) || 20,
  105. max: JSON.parse(localStorage.getItem('tp-maxFPS')) || 200,
  106. random: JSON.parse(localStorage.getItem('tp-randomFPS')) || false,
  107. }
  108. };
  109. function createFolders(NFolder) {
  110. let test = pane.addFolder({
  111. title: NFolder,
  112. expanded: false,
  113. });
  114. return test
  115. };
  116. function hideFPS(value) {
  117. let fpsCounter = document.querySelector('#FPS');
  118. if (value) {
  119. if (fpsCounter) {
  120. fpsCounter.style.display = 'none';
  121. }
  122. } else {
  123. fpsCounter.style.display = 'block';
  124. }
  125. };
  126. function randomise(min, max, active) {
  127. if (active) {
  128. const randomFPS = Math.floor(Math.random() * (max - min + 1)) + min;
  129. let fpsCounter = document.querySelector('#FPS');
  130. if (fpsCounter) {
  131. fpsCounter.textContent = randomFPS;
  132. }
  133. }
  134. };
  135. const makeDraggable = function (element, notMenu) {
  136. if (element) {
  137. let offsetX, offsetY;
  138. element.addEventListener("mousedown", function (e) {
  139. const dragElement = function (e) {
  140. const x = ((e.clientX - offsetX) / unsafeWindow.innerWidth) * 100;
  141. const y = ((e.clientY - offsetY) / unsafeWindow.innerHeight) * 100;
  142. const maxX = 100 - (element.offsetWidth / unsafeWindow.innerWidth) * 100;
  143. const maxY = 100 - (element.offsetHeight / unsafeWindow.innerHeight) * 100;
  144. element.style.left = `${Math.max(0, Math.min(x, maxX))}%`;
  145. element.style.top = `${Math.max(0, Math.min(y, maxY))}%`;
  146. };
  147. if (notMenu || e.target.classList.contains("tp-rotv_t")) {
  148. offsetX = e.clientX - element.getBoundingClientRect().left;
  149. offsetY = e.clientY - element.getBoundingClientRect().top;
  150. document.addEventListener("mousemove", dragElement);
  151. document.addEventListener("mouseup", function () {
  152. document.removeEventListener("mousemove", dragElement);
  153. });
  154. e.preventDefault(); // Prevent text selection during drag
  155. }
  156. });
  157. }
  158. };
  159. //scrambled... geddit????
  160. const getScrambled = function () {
  161. return Array.from({ length: 10 }, () => String.fromCharCode(97 + Math.floor(Math.random() * 26))).join("");
  162. };
  163. const createAnonFunction = function (name, func) {
  164. const funcName = getScrambled();
  165. window[funcName] = func;
  166. F[name] = window[funcName];
  167. functionNames[name] = funcName;
  168. };
  169. const findKeyWithProperty = function (obj, propertyToFind) {
  170. for (const key in obj) {
  171. if (obj.hasOwnProperty(key)) {
  172. if (key === propertyToFind) {
  173. return [key];
  174. } else if (typeof obj[key] === "object" && obj[key] !== null && obj[key].hasOwnProperty(propertyToFind)) {
  175. return key;
  176. }
  177. }
  178. }
  179. // Property not found
  180. return null;
  181. };
  182. const fetchTextContent = function (url) {
  183. var xhr = new XMLHttpRequest();
  184. xhr.open("GET", url, false); // Make the request synchronous
  185. xhr.send();
  186. if (xhr.status === 200) {
  187. return xhr.responseText;
  188. } else {
  189. console.error("Error fetching text content. Status:", xhr.status);
  190. return null;
  191. }
  192. };
  193. const applyLibertyMutual = function (js) {
  194. let hash = CryptoJS.SHA256(js).toString(CryptoJS.enc.Hex);
  195. let clientKeys;
  196. onlineClientKeys = fetchTextContent("https://raw.githubusercontent.com/StateFarmNetwork/client-keys/main/statefarm_" + hash + ".json"); //credit: me :D
  197. clientKeys = JSON.parse(onlineClientKeys);
  198. H = clientKeys.vars;
  199. let injectionString = "";
  200. const modifyJS = function (find, replace) {
  201. let oldJS = js;
  202. js = js.originalReplace(find, replace);
  203. if (oldJS !== js) {
  204. console.log(
  205. "%cReplacement successful! Injected code: " + replace,
  206. "color: green; font-weight: bold; font-size: 0.6em; text-decoration: italic;"
  207. );
  208. } else {
  209. console.log(
  210. "%cReplacement failed! Attempted to replace " + find + " with: " + replace,
  211. "color: red; font-weight: bold; font-size: 0.6em; text-decoration: italic;"
  212. );
  213. }
  214. };
  215. console.log("%cATTEMPTING TO START ????", "color: magenta; font-weight: bold; font-size: 1.5em; text-decoration: underline;");
  216. const variableNameRegex = /^[a-zA-Z_$][a-zA-Z0-9_$]*$/;
  217. for (let name in H) {
  218. deobf = H[name];
  219. if (variableNameRegex.test(deobf)) {
  220. injectionString = `${injectionString}${name}: (() => { let variable = "value_undefined"; try { eval("variable = ${deobf};"); } catch (error) { return "value_undefined"; }; return variable; })(),`;
  221. } else {
  222. }
  223. }
  224. const f = function (varName) {
  225. return varName.replace("$", "\\$");
  226. };
  227. const FUNCTIONPARAM = new RegExp("function " + f(H._connectFail) + "\\(([a-zA-Z$_]+)\\)").exec(js)[1];
  228. console.log(injectionString);
  229. console.log(
  230. "%cSOUNDS INJECTION: INJECT VAR RETRIEVAL FUNCTION AND MAIN LOOP",
  231. "color: yellow; font-weight: bold; font-size: 1.2em; text-decoration: underline;"
  232. );
  233. modifyJS(H.SCENE + ".render", `window["${functionNames.retrieveFunctions}"]({${injectionString}},true)||${H.SCENE}.render`);
  234. console.log(H);
  235. return js;
  236. };
  237. createAnonFunction("retrieveFunctions", function (vars) {
  238. ss = vars;
  239. window.globalSS = ss;
  240. F.HIDEFPS();
  241. });
  242. createAnonFunction("HIDEFPS", function () {
  243. ss.PLAYERS.forEach((PLAYER) => {
  244. if (PLAYER.hasOwnProperty("ws")) {
  245. ss.MYPLAYER = PLAYER;
  246. };
  247. hideFPS(tp.hideFPS.hide);
  248. randomise(tp.hideFPS.min, tp.hideFPS.max, tp.hideFPS.random)
  249. });
  250. H.actor = findKeyWithProperty(ss.MYPLAYER, H.mesh);
  251. });
  252. const Tweakpane = window.Tweakpane;
  253. const pane = new Tweakpane.Pane({
  254. title: "Hide FPS",
  255. expanded: true,
  256. });
  257. const paneEl = document.querySelector("div.tp-dfwv");
  258. paneEl.style.zIndex = 1000;
  259. paneEl.style.width = "300px";
  260. function createInput(obj, property, options, callback) {
  261. pane.addInput(obj, property, options).on('change', callback)
  262. };
  263. makeDraggable(document.querySelector(".tp-dfwv"));
  264. createInput(tp.hideFPS, 'hide', {label: 'Hide FPS'}, (value) => {
  265. localStorage.setItem('tp-hideFPS', JSON.stringify(value.value));
  266. });
  267. createInput(tp.hideFPS, 'random', {label: 'Randomise FPS'}, (value) => {
  268. localStorage.setItem('tp-randomFPS', JSON.stringify(value.value))
  269. })
  270. createInput(tp.hideFPS, 'min', {label: 'Min FPS', view:'slider', min: 1, max: 999, step:1}, (value) => {
  271. localStorage.setItem('tp-minFPS', JSON.stringify(value.value))
  272. });
  273. createInput(tp.hideFPS, 'max', {label: 'Max FPS', view:'slider', min: 1, max: 999, step:1}, (value) => {
  274. localStorage.setItem('tp-maxFPS', JSON.stringify(value.value))
  275. });
  276. document.addEventListener('keydown', (e) => {
  277. if (e.key === 'h') {
  278. const element = document.querySelector('.tp-dfwv');
  279. element.style.display = element.style.display === 'none' ? 'block' : 'none';
  280. }
  281. })
  282. })();