组卷网学科网试卷处理下载打印

【2024/11/16】✨ 自动处理组卷网学科网试卷,并打印,支持去广告,答案分离。

您需要先安装一个扩展,例如 篡改猴Greasemonkey暴力猴,之后才能安装此脚本。

You will need to install an extension such as Tampermonkey to install this script.

您需要先安装一个扩展,例如 篡改猴暴力猴,之后才能安装此脚本。

您需要先安装一个扩展,例如 篡改猴Userscripts ,之后才能安装此脚本。

您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey,才能安装此脚本。

您需要先安装用户脚本管理器扩展后才能安装此脚本。

(我已经安装了用户脚本管理器,让我安装!)

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展,比如 Stylus,才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

您需要先安装一款用户样式管理器扩展后才能安装此样式。

(我已经安装了用户样式管理器,让我安装!)

// ==UserScript==
// @name         组卷网学科网试卷处理下载打印
// @version      2.1.2
// @namespace
// @description  【2024/11/16】✨ 自动处理组卷网学科网试卷,并打印,支持去广告,答案分离。
// @author       nuym
// @match        https://zujuan.xkw.com/zujuan
// @match        https://zujuan.xkw.com/*.html
// @match        https://zujuan.xkw.com/gzsx/zhineng/*
// @match        https://zujuan.xkw.com/share-paper/*
// @icon         https://zujuan.xkw.com/favicon.ico
// @grant        GM_notification
// @require      https://fastly.jsdelivr.net/npm/sweetalert2@11
// @homepage     https://github.com/bzyzh/xkw-zujuan-script
// @license      GNU Affero General Public License v3.0
// @namespace https://github.com/bzyzh
// ==/UserScript==

(function() {
    'use strict';
    console.log("✅ 程序加载成功");

    // 获取用户信息
    var username = document.getElementsByClassName('user-nickname')[0].innerText;
    //var usertype = document.getElementsByClassName('user-type plus')[0].innerText;
    //var endtime = document.getElementsByClassName('end-time')[0].innerText;

    console.log("-----------------------------------------------");
    console.log("🔹版本:2.0.0");
    console.log("🔹作者:nuym");
    console.log("🔹开源地址:https://github.com/bzyzh/xkw-zujuan-script");
    console.log("🔹学校网站:https://www.bzyzh.com");
    console.log("🔹组卷网用户: %s", username);
    console.log("🔹亳州一中学生作品~", username);
    //console.log("🔹组卷网等级: %s", usertype);
    //console.log("🔹组卷网到期时间: %s", endtime);
    console.log("-----------------------------------------------");

    // 去除广告
    var adElement = document.getElementsByClassName("aside-pop activity-btn")[0];
    if (adElement) {
        adElement.remove();
        console.log("✅ 去除广告成功");
    }

    // 签到 TODO:代码逻辑问题(来源于https://greasyfork.org/zh-CN/scripts/497198-%E7%BB%84%E5%8D%B7%E7%BD%91%E8%87%AA%E5%8A%A8%E7%AD%BE%E5%88%B0%E8%84%9A%E6%9C%AC/code)
        function checkIn() {
        var signInBtn = document.querySelector('a.sign-in-btn');
        var daySignInBtn = document.querySelector('a.day-sign-in');

        if (signInBtn) {
            signInBtn.click();
        }

        if (daySignInBtn) {
            daySignInBtn.click();
        }
    }

    function canCheckIn() {
        var signedInLink = document.querySelector('.user-assets-box a.assets-method[href="/score_task/"]');

        // 如果找到了表示已签到的链接,且其文本包含“已签到”,则返回false,否则返回true
        return !signedInLink || signedInLink.textContent !== '已签到';
    }

    function signInLogic() {
        if (canCheckIn()) {
            checkIn();
        }
    }


    function debug() {
        console.log('检查是否可以签到:', canCheckIn());
        console.log('执行签到逻辑:', signInLogic());
    }


    window.addEventListener('load', function() {
        debug();
    }, false);


    // 应用CSS样式
    var style = document.createElement('style');
    style.type = 'text/css';
    style.innerHTML = `
        #zujuanjs-reformatted-content {
            background: white;
        }
        .zujuanjs-question {
            margin-bottom: 10px;
            padding: 10px;
        }
        .zujuanjs-question .left-msg {
            margin-bottom: 5px;
            font-size: 0.8em;
            color: #666;
        }
        #page-title {
            text-align: center;
            font-size: 2em;
            font-weight: bold;
            margin: 20px 0;
        }
    `;
    document.head.appendChild(style);

    // 查找目标元素并将打印按钮添加到目标位置
    console.log("🔹 查找将要添加的位置...");
    var targetElement = document.getElementsByClassName('link-box')[0] || document.getElementsByClassName('btn-box clearfix')[0];
    if (targetElement) {
        console.log("🔹 创建按钮对象...");
        var printButton = document.createElement('a');
        printButton.className = "btnTestDown link-item anchor-font3";
        printButton.innerHTML = `<i class="icon icon-download1"></i><span>打印试卷</span>`;
        targetElement.appendChild(printButton);

        // 绑定点击事件给 printButton
        printButton.onclick = printButtonClickHandler;

        const Toast = Swal.mixin({
            toast: true,
            position: "top-end",
            showConfirmButton: false,
            timer: 3000,
            timerProgressBar: true,
            didOpen: (toast) => {
                toast.onmouseenter = Swal.stopTimer;
                toast.onmouseleave = Swal.resumeTimer;
            },
        });
        Toast.fire({
            icon: "success",
            title: "程序已就绪!",
        });
        console.log("✅ 程序已就绪!");
    } else {
        var targetElementInOtherPlace = document.getElementsByClassName('btn donwload-btn')[0];
        if(targetElementInOtherPlace){
            // 创建新的按钮并添加到试卷下载按钮旁边
            var newPrintButton = document.createElement('a');
            newPrintButton.id = "print-exam";
            newPrintButton.className = "btn";
            newPrintButton.innerHTML = `<i class="icon icon-download"></i><span>打印试卷</span>`;

            // 添加新的按钮到现有的按钮容器中
            var btnBox = document.querySelector('.btn-box');
            if (btnBox) {
            btnBox.appendChild(newPrintButton);

            // 绑定点击事件给 newPrintButton
            newPrintButton.onclick = printButtonClickHandler;
            }
        }else{

            console.error("❌ 无法找到将要添加的位置,程序现在将停止");
            const Toast = Swal.mixin({
                toast: true,
                position: "top-end",
                showConfirmButton: false,
                timer: 3000,
                timerProgressBar: true,
                didOpen: (toast) => {
                    toast.onmouseenter = Swal.stopTimer;
                    toast.onmouseleave = Swal.resumeTimer;
                },
            });
            Toast.fire({
                icon: "error",
                title: "无法找到将要添加的位置,程序现在将停止",
            });
        }
    }

function printButtonClickHandler() {
    Swal.fire({
        title: "是否需要打印答案?",
        showDenyButton: true,
        showCancelButton: true,
        confirmButtonText: "单独打印",
        denyButtonText: `和试题一起打印`,
        cancelButtonText:"仅打印试题",
    }).then((result) => {
        let includeQuestions = false;
        let includeAnswers = false;
        var checkboxSpan = document.querySelector('.tklabel-checkbox.show-answer');

        // 如果找不到答案显示的复选框
        if (!checkboxSpan) {
            includeQuestions = true;
            includeAnswers = false;
            const Toast = Swal.mixin({
                toast: true,
                position: "top-end",
                showConfirmButton: false,
                timer: 3000,
                timerProgressBar: true,
                didOpen: (toast) => {
                    toast.onmouseenter = Swal.stopTimer;
                    toast.onmouseleave = Swal.resumeTimer;
                },
            });
            Toast.fire({
                icon: "error",
                title: "当前页面不支持打印答案,如果需要,请点击分享试卷后打开链接。",
            });
        } else {
            includeAnswers = true;
        }

        // 处理弹窗按钮点击的结果
        if (result.isDenied) {
            // 选中了"和试题一起打印"(即拒绝按钮),但没有答案复选框
            if (!checkboxSpan) {
                includeQuestions = true;
                includeAnswers = false;
                const Toast = Swal.mixin({
                    toast: true,
                    position: "top-end",
                    showConfirmButton: false,
                    timer: 3000,
                    timerProgressBar: true,
                    didOpen: (toast) => {
                        toast.onmouseenter = Swal.stopTimer;
                        toast.onmouseleave = Swal.resumeTimer;
                    },
                });
                Toast.fire({
                    icon: "error",
                    title: "当前页面不支持打印答案,如果需要,请点击分享试卷后打开链接。",
                });
            } else {
                includeQuestions = true;
            }
        } else if (result.isConfirmed) {
            // 如果点击了确认按钮"单独打印"
            if (checkboxSpan) {
                includeQuestions = false;
                includeAnswers = true;
            } else {
                includeQuestions = true;
                includeAnswers = false;
            }
        } else if (result.dismiss === Swal.DismissReason.cancel) {
            // 点击了"取消"按钮,不打印答案,只打印试题
            includeQuestions = true;
            includeAnswers = false;
        }

        // 最终调用打印处理
        handlePrint(includeQuestions, includeAnswers);
    });
}


    function handlePrint(includeQuestions, includeAnswers) {
        if (includeAnswers) {// 修复这里的条件,确保不会无意中赋值
            clickShowAnswersButton();
        }
        var intervalId = window.setInterval(function() {
            if (document.readyState === "complete") {
                clearInterval(intervalId);
                var newPageBody = getReformattedContent(includeQuestions, includeAnswers);
                var titleElement = document.querySelector('.exam-title .title-txt');
                var subject = document.getElementsByClassName('subject-menu__title')[0].innerText;

                if (titleElement) {
                    var pageTitle = titleElement.textContent.trim();
                    var titleDiv = document.createElement('div');
                    titleDiv.id = 'page-title';
                    titleDiv.textContent = pageTitle;
                    newPageBody.insertBefore(titleDiv, newPageBody.firstChild);
                } else {
                    console.log('Title element not found');
                }

                document.body.innerHTML = '';
                document.body.appendChild(newPageBody);
                console.log("✅ 处理成功!");
                GM_notification(subject + ' | ' + pageTitle + "\n ✅ 试卷处理成功!");
                print();
            }
        }, 2000);
    }

    function getReformattedContent(includeQuestions, includeAnswers) {
        var newPageBody = document.createElement('div');
        newPageBody.id = 'zujuanjs-reformatted-content';

        // 获取所有的题目元素
        var questions = document.querySelectorAll('.tk-quest-item.quesroot');

        // 遍历每个题目元素
        questions.forEach(function(question) {
            var newQuestionDiv = document.createElement('div');
            newQuestionDiv.className = 'zujuanjs-question';

            if (includeQuestions) {
                var questionContentDiv = question.querySelector('.wrapper.quesdiv');
                if (questionContentDiv) {
                    newQuestionDiv.appendChild(questionContentDiv.cloneNode(true));
                }
            }



            newPageBody.appendChild(newQuestionDiv);
        });

        return newPageBody;
    }

    function clickShowAnswersButton() {
        var checkboxSpan = document.querySelector('.tklabel-checkbox.show-answer');
        if (checkboxSpan) {
            var checkbox = checkboxSpan.querySelector('input[type="checkbox"]');
            if (checkbox && !checkbox.checked) {
                var label = checkboxSpan.querySelector('label');
                if (label) {
                    label.click();
                }
            }
        }
    }

    // 监听键盘事件--debug用
    document.addEventListener('keydown', function(e) {
        if (e.code === "Escape") {
            var newPageBody = getReformattedContent(true, false);
            var titleElement = document.querySelector('.exam-title .title-txt');
            if (titleElement) {
                var pageTitle = titleElement.textContent.trim();
                var titleDiv = document.createElement('div');
                titleDiv.id = 'page-title';
                titleDiv.textContent = pageTitle;
                newPageBody.insertBefore(titleDiv, newPageBody.firstChild);
            } else {
                console.log('❌ 无法找到题目');
            }
            document.body.innerHTML = '';
            document.body.appendChild(newPageBody);
        }
    });
})();