U校园刷时长-强化版

改编了《U校园刷时长》这个脚本(原作者貌似停止维护)

  1. // ==UserScript==
  2. // @name U校园刷时长-强化版
  3. // @namespace https://blog.1think2program.cn/
  4. // @version 0.7
  5. // @description 改编了《U校园刷时长》这个脚本(原作者貌似停止维护)
  6. // @author DaXue(原作者) - 盧瞳
  7. // @
  8. // @match https://ucontent.unipus.cn/_pc_default/pc.html?cid=*
  9. // @grant none
  10. // @license GPL-3.0
  11. // ==/UserScript==
  12.  
  13. var minTime = [8, 30]; //最短停留时间,默认是3分30秒
  14. var maxTime = [15, 30]; //最大停留时间,默认为5分30秒
  15. var unitInterval = [1, 5]; //循环的单元区间,默认为1-5单元
  16. var maxTestTime = [10, 30]; //单元测试最短停留时间,默认是8分30秒
  17. var minTestTime = [15, 30]; //单元测试最大停留时间,默认为10分30秒
  18. var autojump = 1; //是否开启自动跳过非必修章节功能,0为关闭,1为开启
  19. var feibixiuWaitTime = 15000; //跳过非必修等待的时间,单位毫秒
  20. var jumpTimeOut = 0; //是否开启自动跳过已过截止时间的必修章节
  21. var unitTestStay = 0; //是否单独设置单元测试的时间
  22.  
  23. var feibixiu = document.getElementsByClassName(
  24. "taskTipStyle--disrequired-1ZUIG"
  25. );
  26. var bixiu = document.getElementsByClassName("taskTipStyle--required-23n0J");
  27.  
  28. let waitTime = realTime(minTime[0], minTime[1], maxTime[0], maxTime[1]); // 本次停留时间
  29. let currentUnit = 0; // 当前单元
  30.  
  31. const timer = creatPanel();
  32.  
  33. function switch_next(selector, classFlag) {
  34. let flag = false;
  35. for (let [index, unit] of document.querySelectorAll(selector).entries()) {
  36. if (flag) {
  37. unit.click();
  38. //防止必修弹窗失效,跳转便刷新页面,1000表示跳转1秒后刷新页面
  39. setTimeout(() => {
  40. location.reload();
  41. }, 1000);
  42. flag = false;
  43. break;
  44. }
  45. if (unit.classList.contains(classFlag)) {
  46. flag = true;
  47. }
  48. }
  49. }
  50.  
  51. const sleep = (delay) => new Promise((resolve) => setTimeout(resolve, delay));
  52.  
  53. function jumpToNextSection() {
  54. switch_next(".layoutHeaderStyle--circleTabsBox-jQdMo a", "selected");
  55. switch_next("#header .TabsBox li", "active");
  56. switch_next("#sidemenu li.group", "active");
  57. }
  58.  
  59. // 跳转到开头的第一单元
  60. function jumpToFirstSection() {
  61. console.log("jumpToFirstSection,跳转到第一个单元");
  62. let items = document.querySelectorAll("#sidemenu li.group");
  63. for (let item of items) {
  64. if (getUnitNum(item.textContent) == unitInterval[0]) {
  65. item.click();
  66. break;
  67. }
  68. }
  69. }
  70.  
  71. if (autojump == 1) {
  72. setTimeout(async () => {
  73. if (feibixiu[0].innerText == "非必修") {
  74. // debugger;
  75. // 三十秒后切换,防止检测异常
  76. waitTime = feibixiuWaitTime;
  77. await sleep(feibixiuWaitTime);
  78. jumpToNextSection();
  79. } else if (bixiu[0].innerText == "必修") {
  80. return 0;
  81. }
  82. }, 3000);
  83. }
  84.  
  85. // 自动跳过已过截止时间的必修章节
  86. setTimeout(() => {
  87. try {
  88. var isTestTimeOut = document.getElementsByClassName(
  89. "taskTipStyle--warningheadertext-1ch9A"
  90. );
  91. if (
  92. isTestTimeOut[0].innerText ==
  93. "学习截止时间已过,你可以继续学习,但本次提交得分不计入学习成绩" &&
  94. jumpTimeOut == 1
  95. ) {
  96. jumpToNextSection();
  97. }
  98. } catch (a) {
  99. return 0;
  100. }
  101. }, 3000);
  102.  
  103. //计算实际停留时间,防止每个页面停留时间相同
  104. function realTime(minMinutes, minSeconds, maxMinutes, maxSeconds) {
  105. let rate = Math.random();
  106. return (
  107. (minMinutes * 60 +
  108. minSeconds +
  109. ((maxMinutes - minMinutes) * 60 + maxSeconds - minSeconds) * rate) *
  110. 1000
  111. );
  112. }
  113.  
  114. //自动点击必修弹窗和麦克风弹窗 3000表示延迟3秒,因为弹窗有延迟,主要看反应速度。
  115. setTimeout(() => {
  116. var x = document.getElementsByClassName("dialog-header-pc--close-yD7oN");
  117. x[0].click();
  118. document
  119. .querySelector("div.dialog-header-pc--dialog-header-2qsXD")
  120. .parentElement.querySelector("button")
  121. .click();
  122. }, 3000);
  123.  
  124. // 如果不是在单元区间内,跳转到第一个单元
  125. setTimeout(() => {
  126. // 如果不是在单元区间内,跳转到第一个单元
  127. let unitStr = document.querySelectorAll("#sidemenu li.group.active")[0]
  128. .textContent;
  129.  
  130. currentUnit = getUnitNum(unitStr);
  131.  
  132. if (currentUnit < unitInterval[0] || currentUnit > unitInterval[1]) {
  133. // 不在单元区间内,跳转到第一个单元
  134. console.log("跳转到第一个单元");
  135. let items = document.querySelectorAll("#sidemenu li.group");
  136. for (let item of items) {
  137. if (getUnitNum(item.textContent) == unitInterval[0]) {
  138. console.log("找到第一个单元");
  139. item.click();
  140. break;
  141. }
  142. }
  143. }
  144. }, 3000);
  145.  
  146. setTimeout(() => {
  147. try {
  148. // 单独设置单元测试的时间
  149. var unitTest = document.getElementsByClassName(
  150. "utButtonStyle--toDoButton-1S89L"
  151. );
  152. if (unitTestStay == 1 && unitTest[0].innerText == "开始做题") {
  153. setTimeout(() => {
  154. jumpToNextSection();
  155. }, realTime(minTestTime[0], minTestTime[1], maxTestTime[0], maxTestTime[1]));
  156. }
  157. } catch (e) {
  158. setTimeout(() => {
  159. jumpToNextSection();
  160. }, realTime(minTime[0], minTime[1], maxTime[0], maxTime[1]));
  161. }
  162.  
  163. setInterval(() => {
  164. waitTime -= 1000;
  165. updatePanel();
  166. }, 1000);
  167.  
  168. setTimeout(() => {
  169. jumpToNextSection();
  170. }, waitTime);
  171. }, 4000);
  172.  
  173. function creatPanel() {
  174. let timerPanel = document.createElement("div");
  175. timerPanel.id = "timerPanel";
  176. timerPanel.innerHTML = `
  177. <div id="timerPanelHeader">章节跳转倒计时</div>
  178. <div id="timer">准备开始</div>
  179. <div id="unit">当前单元: </div>
  180. `;
  181. document.body.appendChild(timerPanel);
  182.  
  183. let style = document.createElement("style");
  184. style.innerHTML = `
  185. #timerPanel {
  186. position: fixed;
  187. top: 0;
  188. right: 0;
  189. width: 200px;
  190. height: 100px;
  191. background-color: #f1f1f1;
  192. border: 1px solid #d3d3d3;
  193. z-index: 9999;
  194. text-align: center;
  195. }
  196. #timerPanelHeader {
  197. padding: 2px;
  198. cursor: move;
  199. background-color: #2196F3;
  200. color: #fff;
  201. font-size: 15px;
  202. text-align: center;
  203. height: 40px;
  204. }
  205. #timer {
  206. color: #f00;
  207. line-height: 60px;
  208. font-size: 25px;
  209. }
  210. `;
  211. document.head.appendChild(style);
  212.  
  213. let timerPanelHeader = document.getElementById("timerPanelHeader");
  214. let timer = document.getElementById("timer");
  215. let pos1 = 0,
  216. pos2 = 0,
  217. pos3 = 0,
  218. pos4 = 0;
  219.  
  220. timerPanelHeader.onmousedown = dragMouseDown;
  221.  
  222. function dragMouseDown(e) {
  223. e = e || window.event;
  224. pos3 = e.clientX;
  225. pos4 = e.clientY;
  226. document.onmouseup = closeDragElement;
  227. document.onmousemove = elementDrag;
  228. }
  229.  
  230. function elementDrag(e) {
  231. e = e || window.event;
  232. pos1 = pos3 - e.clientX;
  233. pos2 = pos4 - e.clientY;
  234. pos3 = e.clientX;
  235. pos4 = e.clientY;
  236. timerPanel.style.top = timerPanel.offsetTop - pos2 + "px";
  237. timerPanel.style.left = timerPanel.offsetLeft - pos1 + "px";
  238. }
  239.  
  240. // 在 dragMouseDown 函数中,当鼠标松开时,将面板的位置存储到 localStorage
  241. function closeDragElement() {
  242. document.onmouseup = null;
  243. document.onmousemove = null;
  244. localStorage.setItem("timerPanelTop", timerPanel.style.top);
  245. localStorage.setItem("timerPanelLeft", timerPanel.style.left);
  246. }
  247.  
  248. // 在页面加载时,从 localStorage 中读取面板的位置
  249. window.onload = function () {
  250. let top = localStorage.getItem("timerPanelTop");
  251. let left = localStorage.getItem("timerPanelLeft");
  252. if (top && left) {
  253. timerPanel.style.top = top;
  254. timerPanel.style.left = left;
  255. }
  256. };
  257.  
  258. return timer;
  259. }
  260.  
  261. function getUnitNum(unitStr) {
  262. // let unitStr = document.querySelectorAll("#sidemenu li.group.active")[0]
  263. // .textContent;
  264. let parts = unitStr.split(" ");
  265. let fullNumber = parts[0]; // 获取 "1-1"
  266. let firstNumber = fullNumber.split("-")[0]; // 获取 "1"
  267. firstNumber = parseInt(firstNumber);
  268. return parseInt(firstNumber);
  269. }
  270.  
  271. function updatePanel() {
  272. // 更新倒计时
  273. let milliseconds = waitTime;
  274. let totalSeconds = Math.floor(milliseconds / 1000);
  275. let minutes = Math.floor(totalSeconds / 60);
  276. let remainingSeconds = totalSeconds % 60;
  277. if (remainingSeconds < 10) {
  278. remainingSeconds = "0" + remainingSeconds; // 在一位数前面添加一个 '0'
  279. }
  280. timer.textContent = minutes.toString() + ":" + remainingSeconds.toString();
  281. // 更新单元
  282. document.getElementById("unit").textContent =
  283. "当前单元: " + currentUnit.toString() + "单元";
  284. }

QingJ © 2025

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