User:HarJIT/Scripts/unicategorise.js
// <nowiki>
// Adjust chset-* style code chart colouration to match Unicode categories.
// Adds a button below the source editor.
//
// I am not selling this and make no guarantees of safety, fitness or that it won't mangle the content.
// You are advised to double check that the scripted process has produced the desired results, and
// clean up where necessary (and manually fix the more complicated cases, such as multiple mappings
// or PUA mappings).
//
// Furthermore, this loads JavaScript code from a third-party source for identifying Unicode character
// category. I cannot guarantee that this will not be compromised. Proceed at your own risk.
//
// Usage: mw.loader.load("//en.wikipedia.org/w/index.php?action=raw&ctype=text/javascript&title=User:HarJIT/Scripts/unicategorise.js");
//
// Canonical: [[m:w:User:HarJIT/Scripts/unicategorise.js]]
(() => {
String.prototype.pysplit = function () {
if (arguments.length == 1) {
return this.split(arguments[0]);
}
var temp = this.split(arguments[0], arguments[1]);
var heading = temp.join(arguments[0]).length + arguments[0].length;
temp[temp.length] = this.substring(heading);
return temp;
};
String.prototype.startswith = function (s) {
return this.substring(0, s.length) == s;
};
String.prototype.endswith = function (s) {
return this.substring(this.length - s.length) == s;
};
String.prototype.contains = function (s) {
return this.indexOf(s) >= 0;
};
var ezh = null;
jQuery.get("https://cdn.jsdelivr.net/gh/slevithan/xregexp@57f919a3ebc58ea2f56cb5b2391b6151483b1709/tools/output/categories.js", (b) => {
b = b.pysplit("=", 1)[1].trim();
if (b.endswith(";")) {
b = b.substring(0, b.length-1).trim();
}
ezh = eval(b); // Isn't in the JSON subset, sadly.
}, "text");
var yogh = {};
var doyogh = () => {
if (ezh === null) {
setTimeout(doyogh, 500);
return;
}
ezh.forEach((e) => {
if (typeof e.astral != "undefined") {
yogh[e.name] = new RegExp("[" + e.bmp + "]|" + e.astral);
} else {
yogh[e.name] = new RegExp("[" + e.bmp + "]");
}
});
};
doyogh();
var CHECKMS = "<!-- XXX: check colour -->";
var SHARED = "<!-- Note: Only the shared/invariant EBCDIC cells are colored; international glyphs are not. -->\n";
var FROM = "Invariant alphanumeric, punctuation, and control characters are shown in color.";
var TO = "Non-invariant characters are shown boxed.";
var SUMMARY = "regenerate colour codes based on Unicode category ([[User:HarJIT/Scripts/unicategorise.js|script]])";
var SUMMARY2 = "box nationalised codes, and regenerate colour codes based on Unicode category ([[User:HarJIT/Scripts/unicategorise.js|script]])";
var FAKEHEAD = "|-\n| width=\"4%\" |\n! width=\"6%\" | \u20140 || width=\"6%\" | \u20141\n! width=\"6%\" | \u20142 || width=\"6%\" | \u20143\n! width=\"6%\" | \u20144 || width=\"6%\" | \u20145\n! width=\"6%\" | \u20146 || width=\"6%\" | \u20147\n! width=\"6%\" | \u20148 || width=\"6%\" | \u20149\n! width=\"6%\" | \u2014A || width=\"6%\" | \u2014B\n! width=\"6%\" | \u2014C || width=\"6%\" | \u2014D\n! width=\"6%\" | \u2014E || width=\"6%\" | \u2014F";
var FAKEFOOT = "|-\n||\n!—0||—1||—2||—3||—4||—5||—6||—7||—8||—9||—A||—B||—C||—D||—E||—F";
var fix = function (inp) {
var output = "";
// We need *a* colour template to begin with in order to parse it, even if
// it is the wrong one. For the places where they aren't used already.
// Also some EBCDIC pages use lack of colour as a distinguishing mark, which
// no longer shows up now that -letter is white.
var iox = (inp.contains(SHARED))?("color-intl-box"):("color-intl");
inp = inp.replace(/\n\|\s*\|?\{\{[Cc]hset-c(?=ell|trl)/g, "\n|{{chset-" + iox + "}}|{{chset-c");
var doz = inp.split("{{Chset-").join("{{chset-").split("\n|{{chset-color-");
output += doz[0];
doz.slice(1).forEach((ii) => {
var i = ii;
var nombre = "";
if (i.startswith("undef")) {
output += "\n|{{chset-color-" + ii;
return; /* i.e. continue */
} else if (i.startswith("intl}}|{{chset-cell3||<u>''")) {
// Common in APL code pages, including EBCDIC ones.
output += "\n|{{chset-color-letter" + ii.substring(4);
return; /* i.e. continue */
} else if (i.startswith("hangups}}|{{chset-cell3||<u>''")) {
// What the hell (chset-color-hangups does not exist and afaik never did)
output += "\n|{{chset-color-letter" + ii.substring(7);
return; /* i.e. continue */
} else if (i.substring(0, 40).contains("l4|")) {
nombre = "4";
} else if (i.substring(0, 40).contains("l3|")) {
nombre = "3";
} else if (!i.substring(0, 40).contains("l|")) {
output += "\n|{{chset-color-" + ii;
return; /* i.e. continue */
}
var layout = (i.substring(0, 40).contains("chset-ctrl")) ? ("-ctrl") : ("-cell");
var iii = i.substring(0, 15);
if (iii.startswith("esc")) {
output += "\n|{{chset-color-" + ii;
return; /* i.e. continue */
}
var hilite = ((iii.contains("-box")) ? ("-box") :
((iii.contains("-var")) ? ("-var") : ("")));
if (hilite == "-box" && iii.contains("-box|")) {
hilite += "|" + i.pysplit("-box|", 1)[1].pysplit("}", 1)[0];
}
var wlink = null;
if (nombre === "" && i.pysplit("}}", 1)[1].trim().startswith("|[[")) {
// MIK being _incredibly_ helpful
i = i.pysplit("|[[", 1)[1];
wlink = i.pysplit("|", 1)[0];
i = i.pysplit("|", 2)[2];
} else {
i = i.pysplit("l" + nombre + "|", 1)[1];
}
var cpt = i.pysplit("|", 1)[0].pysplit("}}", 1)[0].trim();
var codept;
if (wlink !== null) {
// MIK being _incredibly_ helpful indeed
var codep = String.fromCodePoint(parseInt(cpt, 16));
i = i.split("}}]]").join("|[[" + wlink + "|" + codep + "]]}}");
}
if (cpt.trim().length === 0 && iii.startswith("ctrl")) {
// Unmapped controls, common in articles about EBCDIC variants.
cpt = "0000"; // Kludgy
}
var cpts = cpt.replace(/<ref[^>]*?(\/>|>[^<]*?<\/ref>)/g, " ");
cpts = cpts.replace(/\(/, "/").replace(/\)/, " ").replace(/\?/, " ");
cpts = cpts.replace(" ", " ").replace(" ", " ").replace(" ", " ").replace(" ", " ");
cpts = cpts.split("/");
var colours = new Set([]);
var checkmsg = "";
cpts.forEach((cpt) => {
cpt = cpt.trim();
if (cpt.contains(" ")) {
cpt = cpt.pysplit(" ", 1)[0];
checkmsg = CHECKMS;
}
if (cpt.match(/^[0-9a-f]+$/i)) {
codept = String.fromCodePoint(parseInt(cpt, 16));
} else {
console.log(cpt); return; /* i.e. continue */
}
if (codept.match(yogh["Co"])) {
// Private use, which could mean:
// (a) An end-user defined character in the source encoding (which would be -misc).
// (b) A well-defined character without a standard Unicode mapping (e.g. the Apple
// logo in Macintosh, the Windows logo in Wingdings, the radical extender in
// x-mac-symbol, several characters in KPS 9566 and LMBCS...).
// ==> Let a human be the judge here.
console.log(cpt); return; /* i.e. continue */
} else if (codept.match(yogh["L"])) {
if (iii.startswith("alpha")) {
// May as well keep it like that for now...
colours.add("-alpha");
} else {
colours.add("-letter");
}
} else if (codept.match(yogh["N"])) {
colours.add("-digit");
} else if (codept.match(yogh["P"])) {
if (iii.startswith("ext") && (parseInt(cpt, 16) > 0x7F)) {
// May as well keep it like that for now...
colours.add("-ext-punct");
} else {
colours.add("-punct");
}
} else if (codept.match(yogh["S"])) {
colours.add("-graph");
} else if (codept.match(yogh["C"])) {
colours.add("-ctrl");
} else {
colours.add("-misc");
}
});
colours = Array.from(colours);
var colour = null;
if (colours.length == 0) {
output += "\n|" + CHECKMS + "{{chset-color-" + ii;
return; /* i.e. continue */
} else if (colours.length == 1) {
colour = colours[0];
} else {
colours.forEach((col) => {
if (iii.startswith(col.substring(1))) {
colour = col;
}
});
if (colour === null) {
output += "\n|" + CHECKMS + "{{chset-color-" + ii;
return; /* i.e. continue */
}
}
output += "\n|" + checkmsg + "{{chset-color" + colour + hilite + "}}|{{chset" + layout + nombre + "|" + i;
});
return output;
};
jQuery(() => {
if (jQuery("#editpage-copywarn").length) {
var butn = document.createElement("input");
butn.setAttribute("type", "button");
butn.setAttribute("value", "Fix chset-color");
var nxt = jQuery("#editpage-copywarn")[0];
nxt.parentNode.insertBefore(butn, nxt);
butn.onclick = () => {
var rprt = SUMMARY;
var txt = jQuery("#wpTextbox1")[0];
var vl = txt.value;
var fx = fix(vl);
if (fx != vl) {
if (vl.contains(SHARED)) {
fx = fx.split(SHARED).join("").split(FROM).join(TO);
rprt = SUMMARY2;
}
var tytl = jQuery("#firstHeading")[0].innerText.trim().substring("Editing ".length);
fx = fx.replace(FAKEHEAD, "{{chset-table-header|" + tytl + "}}");
fx = fx.replace(FAKEFOOT, "{{chset-table-footer}}");
txt.value = fx;
jQuery("#wpSummary")[0].value = rprt;
}
}
}
});
})();
// End: [[m:w:User:HarJIT/Scripts/unicategorise.js]]
// </nowiki>
Content Disclaimer
Informasi ini disarikan dari Wikipedia dan disajikan kembali untuk tujuan edukasi. Konten tersedia di bawah lisensi CC BY-SA 3.0. Kami tidak bertanggung jawab atas ketidakakuratan data yang bersumber dari kontribusi publik tersebut.
- The information displayed on this website is sourced in part or in whole from Wikipedia and has been adapted for the purpose of restating it. We strive to provide accurate and relevant information, however:
- There is no guarantee of absolute accuracy. Wikipedia is an open, collaborative project that can be edited by anyone, so information is subject to change.
- It is not intended to constitute professional advice. The content displayed is for informational and educational purposes only. For important decisions (e.g., medical, legal, or financial), please consult a professional.
- Content copyright. Wikipedia is licensed under the Creative Commons Attribution-ShareAlike License (CC BY-SA). This means that content may be reused with appropriate attribution and shared under a similar license.
- Responsible use. Any risk arising from the use of information from this website is entirely the responsibility of the user.