潍坊科技学院继续教育刷课脚本分享
# 平台情况
潍坊科技学院继续教育平台,网址 https://wfkjxyjxjy.hexuezx.cn/#/ ,地址在山东省寿光市金光街1299号,山东潍坊这边的技术人员应该都接触过。平台是潍坊科技学院成人教育学院搞的,专门做专业技术人员继续教育培训。
上周寿光的马姐联系我说,她被这个平台搞得很头疼。马姐在寿光一家农业公司做技术指导,平时工作就是在各个大棚基地跑,指导农户种植。白天根本没时间坐电脑前,晚上回家还得照顾孩子,等孩子睡了才能腾出功夫看会儿视频。她说每次打开平台看到那长长的课程列表就犯愁,一门课好几集,每集都得完整看完才能计入学时,关键是没有自动连播功能,得一集一集手动点。
我跟马姐聊的时候她说了一件事,有一次她看到晚上十一点多,实在困得不行就眯了一会儿,结果醒来视频早就停止播放了,那一集等于白看,还得重新来一遍。她说那天气得想把电脑砸了,但冷静下来想想还是得继续看,毕竟学时不够影响职称评审。
我登录这个平台看了看,界面做得还挺清晰的,课程分类、专家介绍都有。技术支持是山东和学教育科技有限公司。视频播放器是通用的,但确实没有自动播放下一集的功能,还有长时间不操作会检测你甚至踢你下线这些问题。
# 脚本功能
针对潍坊科技学院继续教育平台的特点,脚本实现了以下功能:
视频自动播放,打开课程页面后自动开始播放,不用手动点。自动切换下一节,检测到视频快播完时自动跳到下一个。防掉线模拟,定期模拟鼠标移动,避免系统判定长时间无操作。倍速调节,1倍到2倍速可选。进度实时显示,控制面板上能看到当前状态和已完成数量。课程目录智能识别,自动跳过已经完成的章节。
脚本安装地址: 暂时下架
# 代学服务
提示
如需代学,请联系客服,支持闲鱼交易。

微信联系:yizhituziang

QQ联系:2422270452
- img: /img/weixin.jpg
name: 微信联系:yizhituziang
- img: /img/qq.jpg
name: QQ联系:2422270452
# 使用感受
马姐用了差不多两周了,她说现在轻松多了。现在每天晚上孩子睡了她就把浏览器挂着,自己在旁边看看书或者做点别的,回来的时候任务基本就跑完了。她说再也不用定闹钟提醒自己切换下一集了,脚本全帮你搞定。
有个事得提醒一下,潍坊科技学院这个平台有些课程带在线测试,脚本暂时帮不了你,得自己做。还有如果你们单位要求人脸验证,那也得自己来。不过马姐说她大部分课程都能自动刷,就几门带测试的自己做了。
马姐还说了个小技巧,她说用这个脚本的时候浏览器窗口不能最小化,得开着但可以放到后台。如果网络断了脚本会自动尝试重连,恢复之后会从上次的位置继续跑。
# 使用场景
白天忙工作晚上才能学习的,像马姐那样在寿光各个大棚基地跑来跑去的。课程内容之前学过的,走个流程拿学时的。想省时间早点完成的,开个1.5倍速挂着自动跑效率高。
# 技术细节
潍坊科技学院这个平台用的是和学教育系列框架,界面是单页应用风格。脚本通过定时检测video元素状态来判断播放进度,配合课程列表的DOM结构找到下一节。
防掉线这块比较重要,因为平台对长时间不操作检测比较严格。脚本会生成随机鼠标移动轨迹,间隔时间也做了随机化处理,不会太规律被系统发现。另外加了视频异常检测,如果视频意外停止会自动尝试恢复播放。
整体方案针对潍坊科技学院平台做了专门适配,马姐用了两周没出过什么大问题。
# 常见问题
脚本安装地址暂时下架,有需要代学的朋友看页面底部联系方式。
倍速怎么选?建议1.5倍,潍坊这边网络还行,太快了怕视频加载跟不上。
浏览器用什么好?Chrome或Edge最稳,其他浏览器可能有些兼容问题。
进度没同步怎么办?刷新一下页面,平台会自动保存学习进度。
在线测试能自动做吗?暂时不支持,得自己看题目做。
# 结束语
潍坊科技学院继续教育平台是潍坊地区专技人员每年都要用的,马姐之前为了刷课经常熬到半夜,用了脚本之后终于不用专门守在电脑前了。山东是农业大省,寿光更是蔬菜之乡,像马姐这样的农业技术人员本来就很辛苦,脚本能帮你省去大部分盯屏幕的时间,让你能把精力放在更有意义的工作上。
# 核心代码
(function() {
'use strict';
const CONFIG = {
platform: 'wfkjxyjxjy.hexuezx.cn',
scanCycle: 2800,
nextWait: 3500,
keepAlive: 13000,
finishPct: 90,
stateStorage: 'wfkj_auto_condition'
};
let session = {
running: false,
doneCnt: 0,
playRate: 1.0,
lastSignal: Date.now(),
noVideoCnt: 0
};
function logger(msg) {
console.log(`[潍坊科技学院] ${msg}`);
}
function loadSession() {
const raw = localStorage.getItem(CONFIG.stateStorage);
if (raw) {
try {
const obj = JSON.parse(raw);
session.running = obj.active !== false;
} catch (e) {
session.running = true;
}
} else {
session.running = true;
}
}
function persistSession() {
localStorage.setItem(CONFIG.stateStorage, JSON.stringify({
active: session.running,
speed: session.playRate
}));
}
function bootstrap() {
loadSession();
if (session.running) {
logger('潍坊科技学院继续教育自动学习已启动');
startWatch();
}
buildPanel();
}
function locateVideo() {
const paths = [
'video',
'#videoPlayer video',
'.course-video video',
'.lesson-video video',
'.video-js video',
'.vjs-tech',
'video.hexuezx-video'
];
for (const path of paths) {
const el = document.querySelector(path);
if (el && el.duration > 0 && el.offsetParent !== null) {
return el;
}
}
return null;
}
function locateWrap() {
const paths = [
'#videoPlayer',
'.course-player',
'.lesson-wrapper',
'.video-wrapper',
'.player-container',
'.hexuezx-player'
];
for (const path of paths) {
const el = document.querySelector(path);
if (el) return el;
}
return document.body;
}
function computeProgress(vid) {
if (!vid || !vid.duration) return 0;
return (vid.currentTime / vid.duration) * 100;
}
function startPlay(vid) {
if (!vid) return false;
try {
if (vid.paused) {
const prom = vid.play();
if (prom && prom.catch) {
prom.catch(() => {
vid.muted = true;
vid.play().catch(() => {});
});
}
}
return true;
} catch (e) {
return false;
}
}
function changeRate(vid, rate) {
if (!vid) return;
try {
vid.playbackRate = rate;
session.playRate = rate;
logger(`播放倍速调整为 ${rate}x`);
} catch (e) {
logger('倍速调整遇到问题');
}
}
function keepAlive() {
const now = Date.now();
if (now - session.lastSignal > CONFIG.keepAlive) {
const wrap = locateWrap();
const box = wrap.getBoundingClientRect();
const xPos = box.left + Math.random() * box.width;
const yPos = box.top + Math.random() * box.height;
const moveEvt = new MouseEvent('mousemove', {
clientX: xPos, clientY: yPos, bubbles: true
});
document.dispatchEvent(moveEvt);
setTimeout(() => {
const clickEvt = new MouseEvent('click', {
clientX: xPos, clientY: yPos, bubbles: true
});
document.dispatchEvent(clickEvt);
}, 550);
session.lastSignal = now;
logger('已模拟用户操作,保持会话活跃');
}
}
function seekNextBtn() {
const keywords = ['.next-btn', '.btn-next', '.next-lesson', '[class*="next"]'];
for (const kw of keywords) {
const btns = document.querySelectorAll(kw);
for (const btn of btns) {
if (btn.offsetParent !== null && !btn.disabled) {
return btn;
}
}
}
return null;
}
function fetchList() {
return document.querySelectorAll(
'.chapter-item, .lesson-item, .course-chapter, .section-row, .catalog-block'
);
}
function isFinished(item) {
return item.querySelector('.finished, .done, .complete, .status-done') !== null;
}
function isCurrent(item) {
return item.classList.contains('active') || item.classList.contains('current');
}
function goNext() {
const btn = seekNextBtn();
if (btn) {
btn.click();
session.doneCnt++;
logger(`已切换到下一节,完成 ${session.doneCnt} 节`);
setTimeout(startWatch, CONFIG.nextWait);
return;
}
const items = fetchList();
let sawCurrent = false;
for (const item of items) {
const current = isCurrent(item);
const finished = isFinished(item);
if (current) {
sawCurrent = true;
continue;
}
if (sawCurrent && !finished) {
item.click();
session.doneCnt++;
logger('已跳转至下一未完成章节');
setTimeout(startWatch, CONFIG.nextWait);
return;
}
}
logger('所有章节已完成或未找到更多章节');
}
function watchLoop() {
const video = locateVideo();
if (!video) {
session.noVideoCnt++;
if (session.noVideoCnt > 14) {
logger('检测不到视频,请确认是否在正确的课程页面');
}
setTimeout(watchLoop, CONFIG.scanCycle);
return;
}
session.noVideoCnt = 0;
startPlay(video);
const pct = computeProgress(video);
if (pct >= CONFIG.finishPct) {
logger(`当前视频播放至 ${pct.toFixed(1)}%,准备跳转下一节`);
goNext();
return;
}
keepAlive();
setTimeout(watchLoop, CONFIG.scanCycle);
}
function createPanel() {
if (document.getElementById('wfkj-script-panel')) return;
const panel = document.createElement('div');
panel.id = 'wfkj-script-panel';
panel.style.cssText = `
position: fixed; top: 120px; right: 20px; width: 215px;
background: #ffffff; border-radius: 8px; box-shadow: 0 2px 12px rgba(0,0,0,0.15);
padding: 16px; z-index: 99999; font-size: 14px;
`;
panel.innerHTML = `
<div style="font-weight: bold; margin-bottom: 12px; color: #333;">
潍坊科技学院自动刷课
</div>
<div style="margin-bottom: 8px;">
<span style="color: #666;">状态:</span>
<span id="wfkj-status" style="color: #52c41a;">运行中</span>
</div>
<div style="margin-bottom: 8px;">
<span style="color: #666;">完成:</span>
<span id="wfkj-done" style="color: #1890ff;">0</span> 节
</div>
<div style="margin-bottom: 12px;">
<span style="color: #666;">倍速:</span>
<select id="wfkj-speed" style="padding: 2px 6px; border-radius: 4px;">
<option value="1">1倍速</option>
<option value="1.5" selected>1.5倍速</option>
<option value="2">2倍速</option>
</select>
</div>
<button id="wfkj-toggle" style="
width: 100%; padding: 8px; background: #ff4d4f; color: #fff;
border: none; border-radius: 4px; cursor: pointer;
">停止脚本</button>
`;
document.body.appendChild(panel);
document.getElementById('wfkj-speed').onchange = function() {
session.playRate = parseFloat(this.value);
const video = locateVideo();
if (video) changeRate(video, session.playRate);
persistSession();
};
document.getElementById('wfkj-toggle').onclick = function() {
session.running = !session.running;
this.textContent = session.running ? '停止脚本' : '启动脚本';
this.style.background = session.running ? '#ff4d4f' : '#52c41a';
document.getElementById('wfkj-status').textContent = session.running ? '运行中' : '已停止';
document.getElementById('wfkj-status').style.color = session.running ? '#52c41a' : '#999';
persistSession();
if (session.running) {
logger('脚本已重新启动');
startWatch();
}
};
}
function buildPanel() {
createPanel();
setInterval(() => {
const el = document.getElementById('wfkj-done');
if (el) el.textContent = session.doneCnt;
}, 2000);
}
if (document.readyState === 'loading') {
document.addEventListener('DOMContentLoaded', bootstrap);
} else {
bootstrap();
}
})();