User:Slowking Man/scripts/ReallyComplete.js
Appearance
Code that you insert on this page could contain malicious content capable of compromising your account. If you import a script from another page with "importScript", "mw.loader.load", "iusc", or "lusc", take note that this causes you to dynamically load a remote script, which could be changed by others. Editors are responsible for all edits and actions they perform, including by scripts. User scripts are not centrally supported and may malfunction or become inoperable due to software changes. A guide to help you find broken scripts is available. If you are unsure whether code you are adding to this page is safe, you can ask at the appropriate village pump. This code will be executed when previewing this page. |
![]() | Documentation for this user script can be added at User:Slowking Man/scripts/ReallyComplete. |
// <syntaxhighlight lang="javascript">
// <nowiki>
// LICENSE: CC0
// ES6-ified for great justice
// MW requires ES6 these days or else disables JS
$( () =>
{ // when whole thing wrapped in a func I figure why stuff it full of extraneous whitesp
'use strict';
const whoami = 'AutoEd/ReallyComplete.js';
const writeToLog = ( type = 'warn' , ...args ) =>
{
const logFn = mw.log[ type ];
logFn( `In ${whoami}:/n` , args );
};
const errLog = ( ...x ) => writeToLog( 'error' , x );
const warnLog = ( ...x ) => writeToLog( 'warn' , x );
try {
const reqMods = 'jquery.textSelection' ,
myloader = async mods => await mw.loader.using( mods );
myloader( reqMods );
const baseurl = '//wiki.riteme.site/w/index.php?action=raw&\
ctype=text/javascript&';
const AutoEdModule = class
{
// this is ES2022 stuff but hopefully no one trying to use with old browser
// that's why WP's builtin JS editor doesn't grok it,
// its definitions are out of date
static #loadFn = mw.loader.load;
static #baseAutoEd = 'title=Wikipedia:AutoEd/';
static #core = 'core.js';
static get baseAutoEd() { return this.#baseAutoEd; }
#name;
#url;
#entryPt; // pre-emptive forward-compatibility
#myWin; // you'll see in second
get name() { return this.#name; }
get url() { return this.#url ??
AutoEdModule.#assembleUrl( this.#name ); }
get entryPt()
{
return this.#entryPt ??
myWin[ 'autoEd' + this.#name ];
} // get entryPt()
// think of above as a modern eval()
// which is Considered Harmful for numerous reasons
// did you know calling it can make many JS engine optimizations impossible
// it can produce "self-modifying code",
// which violates many assumptions relied upon by compilers to optimize code
// https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/eval
// If you have no idea what is going on here:
// when running in "Web context", globals are defined on the global Window object
// so by default (when #entryPt undef)
// this assumes the module's entry func is "the usual"
// and returns the global entry pt func the module defined
// accessing it from global window w/ property accessor syntax
// as a computed property - computed from module name & usual name prefix (*whew*)
// You know good ol' console.log, window.close & friends
// Those are just methods, defined on those global console/window/etc objs
// you can even redefine them if you want
// disclaimer you are responsible for any Fun Stuff that happens as result
// (you are accessing them w/ "dot syntax", see also eg this.myCoolFunc();)
// in JS Everything Is An Object(tm) (terms & conditions apply)
// more forward-compat, when not running in something like browser (Node.js anyone?)
// there may be no global window defined
// this way if run under smth else it can pass in own "window" if it wants
// (or just define global one)
get myWin()
{ return this.#myWin ??
window?.window; }
// ?. = "optional chaining" it's . but returns undef if left side is undef
// if you do foo.bar and foo is undef it throws exception
// (for ex consumer of class might want to chk value and branch based on if defined)
// helper method
static #assembleUrl( modName )
{ return baseurl + this.baseAutoEd + modName.toLowerCase() +
modName.includes('.') ? '' : '.js'; }
// appends .js if no file extension
static #load( ...mods )
{ mods.forEach( curItem => this.#loadFn(
this.#assembleUrl( curItem.name ) ) ); }
// come on you know I was gonna give all these features a workout :)
// static initializer block
// runs once, when class is well, "initialized" by JS engine
// so let's load core here now watch this
static
{ this.#load( this.#core ); }
// rest parameter syntax
constructor( ...args )
{
// and, array unpacking, together quite powerful and handy!
// "don't repeat yourself"
[ this.#name ,
this.#url ,
this.#entryPt ,
this.#myWin , ] = args;
} // constructor
} ; // AutoEdModule
const AutoEdMods = [ 'Unicodify' ,
'ISBN' ,
'Whitespace' ,
'UnicodeHex' ,
'Wikilinks' ,
'HTMLtoWikitext' ,
'Headlines' ,
'UnicodeControlChars' ,
'Templates' ,
'TablestoWikitext' ,
'ExtraBreaks' ,
'Fullwidth' ,
'Links' ,
// [ 'CurlyFixer' , '/* todo */' ] ,
];
// trailing , is legal & ignored, helpful lil trick to reduce forgetfulness errs
// entry pt func to be installed
const edFunc = ( mods = AutoEdMods ) =>
{
try {
// turn mod list array into array of objects
// yep another arrow func, very common ES6+ idiom
// which is why the syntax is defined that way, to cut down on boilerplate
mods = Array.from( mods, x => new AutoEdModule(x) );
const $textbox = $( '#wpTextbox1' ) ,
ts = $textbox.textSelection;
let txt = ts( 'getContents' );
for( const curMod of mods ) { txt = curMod.entryPt( txt ); }
ts( 'setContents' , txt );
// see isn't that nice and compact
} // edFunc try
catch( e )
{ errLog( e ); }
return;
}; // edfunc
// install global func
// note: this assumes install on global window
window.autoEdFunctions = edFunc;
} // try
catch( e )
{ errLog( e ); }
return;
} ); // $( () => {
// </nowiki>
// </syntaxhighlight>