ZUA课表导出

导出郑州航院课程表为ics文件

当前为 2020-02-26 提交的版本,查看 最新版本

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

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

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

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

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

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

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

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

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

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

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

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

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

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

// ==UserScript==
// @name         ZUA课表导出
// @namespace    http://tampermonkey.net/
// @version      0.1
// @description  导出郑州航院课程表为ics文件
// @author       yangwu
// @match        http://202.196.166.135/*
// @match        http://202.196.166.136/*
// @match        http://202.196.166.138/*
// @match        http://202.196.166.139/*
// @grant        none
// ==/UserScript==

(function () {
    'use strict';
    const CRLF = "\r\n"
    function time_Deal(a) {//时间处理
        var class_begin;
        var class_end;
        var week_begin;
        var week_end;
        var week_one;
        var class1;
        var week1;
        week_one = a[1];
        class1 = a.match(/第.*节{/)[0];
        week1 = a.match(/{第.*周/)[0];
        class_begin = class1.substring(1, class1.indexOf(","));
        class_end = class1.substring(class1.indexOf(",") + 1, class1.length - 2);
        week_begin = week1.substring(2, week1.indexOf("-"));
        week_end = week1.substring(week1.indexOf("-") + 1, week1.length - 1);
        a = new Array();
        a.push(week_one);
        a.push(class_begin);
        a.push(class_end);
        a.push(week_begin);
        a.push(week_end);
        return a;
    }//时间处理
    //***************************************
    function weekswitch(i) {
        switch (i) {
            case '日': i = 6;
                break;
            case '一': i = 0;
                break;
            case '二': i = 1;
                break;
            case '三': i = 2;
                break;
            case '四': i = 3;
                break;
            case '五': i = 4;
                break;
            case '六': i = 5;
                break;
        }
        return i;
    }
    function classEndSwitch(i) {
        switch (i) {
            case '1': i = '0845';
                break;
            case '2': i = '0940';
                break;
            case '3': i = '1045';
                break;
            case '4': i = '1140';
                break;
            case '5': i = '1515';
                break;
            case '6': i = '1610';
                break;
            case '7': i = '1715';
                break;
            case '8': i = '1810';
                break;
            case '9': i = '2015';
                break;
            case '10': i = '2110';
                break;
        }
        return i;
    }
    function classBeginSwitch(i) {
        switch (i) {
            case '1': i = '0800';
                break;
            case '2': i = '0855';
                break;
            case '3': i = '1000';
                break;
            case '4': i = '1055';
                break;
            case '5': i = '1430';
                break;
            case '6': i = '1525';
                break;
            case '7': i = '1630';
                break;
            case '8': i = '1725';
                break;
            case '9': i = '1930';
                break;
            case '10': i = '2025';
                break;
        }
        return i;
    }
    function data_get() {
        var iframe = window.top.document.getElementById('iframeautoheight');
        var ifdocument = iframe.contentWindow.document;
        var couse = ifdocument.getElementsByClassName("datelist ");
        var couses = new Array;
        for (var i = 0; i < couse[0].rows.length; i++) {
            couses[i] = new Array;
            for (var j = 0; j < 10; j++) {
                var info = couse[0].rows[i].cells[j].innerHTML;
                couses[i].push(info);
            }
        }
        var data = new Array;
        for (i = 0; i < couses.length; i++) {
            data[i] = new Array;
            data[i].push(couses[i][2]);//课程名称
            data[i].push(couses[i][5]);//教师
            data[i].push(couses[i][8]);//时间
            data[i].push(couses[i][9]);//地点
        }
        for (i = 1; i < data.length; i++) {
            data[i][0] = data[i][0].match(/>.*</)[0].substring(1, data[i][0].match(/>.*</)[0].length - 1);
            data[i][1] = data[i][1].match(/>.*</)[0].substring(1, data[i][1].match(/>.*</)[0].length - 1);
            data[i][2] = data[i][2].match(/>.*</)[0].substring(1, data[i][2].match(/>.*</)[0].length - 1);
        }
        return data
    }
    //数据获取
    //**************************************
    function classDorS(b) {
        if (b.indexOf(";") != -1) {//存在;即为多节课
            b = b.split(";")
        }
        return b;
    }//多节判断
    //*********************************************
    function dataDeal(a) {
        for (var i = 1; i < a.length; i++) {
            a[i][2] = classDorS(a[i][2]);
            a[i][3] = classDorS(a[i][3]);
            if (a[i][2].length < 5) {
                for (var j = 0; j < a[i][2].length; j++) {
                    a[i][2][j] = time_Deal(a[i][2][j]);
                }
            }
            else {
                a[i][2] = time_Deal(a[i][2]);
            }
        }
        return a;

    }
    function firstD(d) {
        var nian = d.split("-");
        var c = new Date();
        c.setFullYear(nian[0], nian[1] - 1, nian[2]);
        return c;
        console.log(c);
    }
    function kaishiriqi(a, b) {
        var c = new Date();
        c.setDate(firstD(b).getDate() + weekswitch(a[0]) + (a[3] - 1) * 7);
        Date.prototype.format = function (fmt) {
            var o = {
                "M+": this.getMonth() + 1,
                "d+": this.getDate(),
                "h+": this.getHours(),
                "m+": this.getMinutes(),
                "s+": this.getSeconds(),
                "q+": Math.floor((this.getMonth() + 3) / 3),
                "S": this.getMilliseconds()
            };

            if (/(y+)/.test(fmt)) {
                fmt = fmt.replace(RegExp.$1, (this.getFullYear() + "").substr(4 - RegExp.$1.length));
            }

            for (var k in o) {
                if (new RegExp("(" + k + ")").test(fmt)) {
                    fmt = fmt.replace(
                        RegExp.$1, (RegExp.$1.length == 1) ? (o[k]) : (("00" + o[k]).substr(("" + o[k]).length)));
                }
            }

            return fmt;
        }
        c = c.format("yyyyMMdd");
        return c;
        console.log(c);
    }
    function genFinal(init) {
        var result = "";
        for (var i = 0; i < init.length; ++i) {
            var finalLine = "";
            var line = init[i];
            var len = line.length;
            if (len > 60) {
                var remain_len = len;
                var index = 0;
                while (remain_len > 0) {
                    for (var j = 0; j < index; ++j)
                        result += SPACE;
                    result += line.slice(0, 60);
                    line = line.slice(61);
                    remain_len -= 60;
                    index++;
                }
                line.slice(0, 60);
            }
            else
                finalLine = line;
            result += line + CRLF;
        }
        return result;
    }
    function icsdata(a, c) {
        var b = new Array;
        b.push("BEGIN:VCALENDAR");
        b.push("PRODID:-//TypeScript/Node.js//ZUA Course Exporter v1.0//CN");
        b.push("VERSION:2.0");
        for (var i = 1; i < a.length; i++) {
            if (a[i][2] != "") {
                if (a[i][2].length != 5) {
                    for (var j = 0; j < a[i][2].length; j++) {
                        b.push("BEGIN:VEVENT");
                        b.push("LOCATION:" + a[i][3][j]);
                        b.push("DTSTART;TZID='China Standard Time':" + kaishiriqi(a[i][2][j], c) + 'T' + classBeginSwitch(a[i][2][j][1]) + '00');
                        b.push("DTEND;TZID='China Standard Time':" + kaishiriqi(a[i][2][j], c) + 'T' + classEndSwitch(a[i][2][j][2]) + '00');
                        b.push("SUMMARY;LANGUAGE=zh-cn:" + a[i][0] + "(" + a[i][1] + ")");
                        if(a[i][2][j][4].search("单")!=-1||a[i][2][j][4].search("双")!=-1){
                            b.push("RRULE:FREQ=WEEKLY;COUNT="+((a[i][2][j][4].match(/\d+/i)-a[i][2][j][3])/2+1)+";INTERVAL=2")
                        }else if(a[i][2][j][4].search("单")==-1 && a[i][2][j][4].search("双")==-1){
                            b.push("RRULE:FREQ=WEEKLY;COUNT="+(a[i][2][j][4].match(/\d+/i)-a[i][2][j][3]+1))
                        }
                        b.push("END:VEVENT");
                    }
                }
                else {
                    b.push("BEGIN:VEVENT");
                    b.push("LOCATION:" + a[i][3]);
                    b.push("DTSTART;TZID='China Standard Time':" + kaishiriqi(a[i][2], c) + 'T' + classBeginSwitch(a[i][2][1]) + '00');
                    b.push("DTEND;TZID='China Standard Time':" + kaishiriqi(a[i][2], c) + 'T' + classEndSwitch(a[i][2][2]) + '00');
                    b.push("SUMMARY;LANGUAGE=zh-cn:" + a[i][0] + "(" + a[i][1] + ")");
                    if(a[i][2][4].search("单")!=-1||a[i][2][4].search("双")!=-1){
                        b.push("RRULE:FREQ=WEEKLY;COUNT="+((a[i][2][4].match(/\d+/i)-a[i][2][3])/2+1)+";INTERVAL=2")
                    }else if(a[i][2][4].search("单")==-1 && a[i][2][4].search("双")==-1){
                        b.push("RRULE:FREQ=WEEKLY;COUNT="+(a[i][2][4].match(/\d+/i)-a[i][2][3]+1))
                    }
                    b.push("END:VEVENT");
                }

            }

        }
        b.push("END:VCALENDAR");
        console.log(b);
        return b;
    }
    function danshuang(a){
        for(var i=1;i<a.length;i++){
            if(a[i][2].length!=5){
                for(var j=0;j<a[i][2].length;j++){
                    if(a[i][2][j][4].search("双")!=-1){
                        if(a[i][2][j][3]%2!=0){
                            a[i][2][j][3]=String(Number(a[i][2][j][3])+1);
                        }
                    }
                }
            }else if(a[i][2][4].search("双")!=-1){
                if(a[i][2][3]%2!=0){
                    a[i][2][3]=String(Number(a[i][2][3])+1);
                }
            }
        }
        return a;
    }
    const PAGE = {
        "main": /xs_main.aspx/,
        "course_table": /xsxkqk.aspx/
    };
    const iframe = document.querySelector("#iframeautoheight");
    if (iframe) {
        iframe.addEventListener('load', function () {
            const content = iframe.contentDocument || iframe.contentWindow.document;
            const URL = content.location.href;
            if (PAGE["course_table"].test(URL)) {
                const inject_td = content.querySelector('.search_con');
                const inject_p = content.createElement("p");
                const export_span = content.createElement("span");
                const export_first_day = content.createElement('input');
                const export_btn = content.createElement('button');
                const dwn_anchor = content.createElement("a");
                dwn_anchor.innerHTML = "Download the .ics file";
                dwn_anchor.style.visibility = "hidden";
                inject_p.appendChild(export_span);
                inject_p.appendChild(export_first_day);
                inject_p.appendChild(export_btn);
                inject_p.appendChild(dwn_anchor);
                inject_td.appendChild(content.createElement("br"));
                inject_td.appendChild(inject_p);
                export_span.innerHTML = "   这个学期的第一个星期一是:";
                export_first_day.type = "date";
                export_first_day.value = "2020-02-24";
                export_btn.innerText = "导出课表";
                export_btn.addEventListener('click', (evt) => {
                    evt.preventDefault();
                    var data_1 = data_get();
                    dataDeal(data_1);
                    data_1=danshuang(data_1);
                    console.log(data_1);
                    dwn_anchor.style.visibility = "visible";
                    var result = genFinal(icsdata(data_1, export_first_day.value));
                    var link = window.URL.createObjectURL(new Blob([result], {
                        type: "text/x-vCalendar"
                    }));
                    dwn_anchor.setAttribute("href", link);
                    dwn_anchor.setAttribute("download", "cal.ics");
                })
            }
        })
    }

    // Your code here...
})();