Mug Helper

Makes mugging easier

  1. // ==UserScript==
  2. // @name Mug Helper
  3. // @namespace http://tampermonkey.net/
  4. // @license NOLICENSE
  5. // @version 0.2
  6. // @description Makes mugging easier
  7. // @author Harmageddon
  8. // @match https://www.torn.com/*
  9. // @grant GM_addStyle
  10. // @grant GM_xmlhttpRequest
  11. // @grant GM.xmlHttpRequest
  12. // @run-at document-end
  13. // ==/UserScript==
  14.  
  15. let API_KEY = "";
  16.  
  17. const waitForElement = (selector) => {
  18. return new Promise(resolve => {
  19. if (document.querySelector(selector)) {
  20. return resolve(document.querySelector(selector));
  21. }
  22.  
  23. const observer = new MutationObserver(mutations => {
  24. if (document.querySelector(selector)) {
  25. resolve(document.querySelector(selector));
  26. observer.disconnect();
  27. }
  28. });
  29.  
  30. observer.observe(document.body, {
  31. childList: true,
  32. subtree: true
  33. });
  34. });
  35. };
  36.  
  37. const getRequestAsync = (url) => {
  38. return new Promise((resolve, reject) => {
  39. GM_xmlhttpRequest({
  40. method: "GET",
  41. url: url,
  42. onload: function(response) {
  43. resolve(response.responseText);
  44. },
  45. onerror: function(error) {
  46. reject(error);
  47. }
  48. });
  49. });
  50. }
  51.  
  52. const waitForElements = (selector, action, container, timeControl) => {
  53. let targetNodes = (container ?? document).querySelectorAll(selector);
  54.  
  55. if (targetNodes && targetNodes.length > 0) {
  56. targetNodes.forEach(function (node) {
  57. let alreadyFound = node.getAttribute('data-found') || false;
  58.  
  59. if (!alreadyFound) {
  60. if (!action(node)) {
  61. node.setAttribute('data-found', true);
  62. }
  63. }
  64. });
  65. }
  66.  
  67. if (!timeControl) {
  68. timeControl = setInterval(() => {
  69. waitForElements(selector, action, container, timeControl);
  70. }, 300);
  71. }
  72. };
  73.  
  74. const JSONparse = (str) => {
  75. try {
  76. return JSON.parse(str);
  77. } catch (e) {}
  78. return null;
  79. }
  80.  
  81. const inject_initial_html = () => {
  82.  
  83.  
  84. };
  85.  
  86. const check_cloting_store = () => {
  87. const check_status = () => {
  88. let urlParams = new URLSearchParams(window.location.search);
  89. let userID = urlParams.get('user2ID');
  90. //const url = `https://api.torn.com/user/${userID}?selections=basic,icons&key=${API_KEY}`;
  91. const url = `https://api.torn.com/user/${userID}?&key=${API_KEY}`;
  92. GM.xmlHttpRequest(
  93. {
  94. method: 'POST',
  95. url: url,
  96. onload: function (response)
  97. {
  98. if (response.status == '200')
  99. {
  100. const data = JSON.parse(response.responseText);
  101. const containsCompanyClothingStore = Object.values(data.basicicons).some(value =>
  102. value.toLowerCase().includes("company") && value.toLowerCase().includes("(clothing store)")
  103. );
  104. // Add span only if it doesn't already exist
  105. if (containsCompanyClothingStore)
  106. {
  107.  
  108. const companyUrl = `https://api.torn.com/company/${data.job.company_id}?&key=${API_KEY}`;
  109. GM.xmlHttpRequest(
  110. {
  111. method: 'POST',
  112. url: companyUrl ,
  113. onload: function (response)
  114. {
  115. if (response.status == '200')
  116. {
  117. const companyData = JSON.parse(response.responseText)
  118. if(companyData.company.rating >= 7)
  119. {
  120. injectFlashingCSS();
  121. const container = document.querySelector('.title___rhtB4');
  122. if (container && container.textContent.includes('Attacking') && !container.querySelector('.clothing-store-span'))
  123. {
  124. const span = document.createElement('span');
  125. span.className = 'clothing-store-span flashing-text'; // Add a unique and flashing class
  126. span.textContent = 'Clothing Store Mug Protection is active';
  127. span.style.color = "red";
  128. container.appendChild(span);
  129. }
  130. }
  131. }
  132. }
  133. });
  134. }
  135. }
  136. }
  137. });
  138. };
  139. function injectFlashingCSS()
  140. {
  141. const css = `
  142. @keyframes flash {
  143. 0% { opacity: 1; }
  144. 50% { opacity: 0; }
  145. 100% { opacity: 1; }
  146. }
  147.  
  148. .flashing-text {
  149. animation: flash 1s infinite;
  150. }
  151. `;
  152.  
  153. const style = document.createElement('style');
  154. style.textContent = css;
  155. document.head.appendChild(style);
  156. }
  157. check_status();
  158. };
  159.  
  160.  
  161.  
  162.  
  163. const init = () => {
  164. check_cloting_store();
  165. };
  166.  
  167. (function() {
  168. 'use strict';
  169. inject_initial_html();
  170. if (API_KEY) {
  171. init();
  172. }
  173. })();