User:Amousey/common.js

// ==UserScript== // @name        This Ain't A Phone // @namespace   https://schiff.io // @version      9 // @description Automatically redirect from mobile webpages to the non-mobile equivalent // @author      Hayden Schiff (oxguy3) // @match       *://m.mediawiki.org/* // @match       *://*.m.wikimedia.org/* // @match       *://*.m.wikipedia.org/* // @grant       none // @run-at      document-start // ==/UserScript==

(function {   'use strict';

// Checks if the location is a mobile site, and returns the URL of the non-mobile equivalent // Params: loc: window.location // Returns: string of new URL, or false if no match function checkLocation(loc) {

// simple hostname replacement rules var hostRules = [ [ 'm.mediawiki.org', 'www.mediawiki.org' ], [ 'en.m.wikipedia.org', 'en.wikipedia.org' ] ];

// shared logic for sites that only require a changed hostname for (var i = 0; i < hostRules.length; i++) { var rule = hostRules[i]; if (loc.host == rule[0]) { return loc.href.replace('//'+rule[0], '//'+rule[1]); }       }

// special logic for Wikimedia sites (too many subdomains to list individually) var wikimediaHosts = [ 'wikipedia.org', 'wikimedia.org' ];       for (var i = 0; i < wikimediaHosts.length; i++) { var wmHost = wikimediaHosts[i]; if (loc.host.endsWith('.m.'+wmHost)) { var newHost = loc.host.slice(0, 0 - ('m.'+wmHost).length) + wmHost; return loc.protocol + "//" + newHost + ":" + loc.port + loc.pathname + loc.search + loc.hash; }       }

return false; }

var destination = checkLocation(window.location); if (destination !== false) { window.location.href = destination; } });

// de Wikipedia veAutocorrect.js //Dokumentation unter Benutzer:Schnark/js/veAutocorrect /*global mediaWiki, OO, ve*/ (function (mw) { "use strict";

var VISUAL = 1, SOURCE = 2, deps;

function initAutoCorrect (lang, wiki) { var autoCorrectCommandCount = 0, quotes, i;

//like ve.ui.Sequence, with the difference that for regular expressions //of the form /foo(bar)/ only the parentheses is used as Range, not the whole expression function ReSequence { ReSequence.parent.apply(this, arguments); }	OO.inheritClass(ReSequence, ve.ui.Sequence); ReSequence.prototype.match = function (data, offset, plaintext) { var execResult; if (this.data instanceof RegExp) { execResult = this.data.exec(plaintext); return execResult && new ve.Range(offset - execResult[1].length, offset); }		return ReSequence.parent.prototype.match.apply(this, arguments); };

//when the user enters "from" change it to "to" //from can be a string, a regular expression of the form /foo(bar)/ or an array of data //to can be a string or an array of data //strip is the number of chars to strip //mode defaults to both VISUAL and SOURCE function autoCorrectFromTo (from, to, strip, mode) { //get a unique name, we use it for both the command and the sequence var name = 'schnarkAutoCorrectCommand-' + (autoCorrectCommandCount++), seq; //create and register the command ve.ui.commandRegistry.register(			//1st true: annotate, 2nd true: collapse to end			new ve.ui.Command(name, 'content', 'insert', {args: [to, true, true]})		); //create and register the sequence seq = new ReSequence(/*sequence*/ name, /*command*/ name, from, strip); if (!mode || mode === VISUAL) { ve.ui.sequenceRegistry.register(seq); }		if ((!mode || mode === SOURCE) && ve.ui.wikitextSequenceRegistry) { ve.ui.wikitextSequenceRegistry.register(seq); }	}

//define what should be autocorrected quotes = { de: ['„', '“'], en: ['“', '”'], it: ['“', '”'] };

//for all languages and projects autoCorrectFromTo(/(?:^|[^!])(--)$/, '–', 2); //don't mess with ', 2, SOURCE); //fix --> (only needed for source code)	autoCorrectFromTo('–-', '—', 2); //--- with -- turned into –	autoCorrectFromTo('—-', , 2, SOURCE); //keep in source code	autoCorrectFromTo('...', '…', 3);	autoCorrectFromTo('<<', '«', 2);	autoCorrectFromTo('>>', '»', 2);	autoCorrectFromTo('->', '→', 2);	autoCorrectFromTo(' 1/2 ', ' ½ ', 5);	autoCorrectFromTo(' 1/4 ', ' ¼ ', 5);	autoCorrectFromTo(' 3/4 ', ' ¾ ', 5);	autoCorrectFromTo('+-', '±', 2);	autoCorrectFromTo(/\d(')$/, '′', 1);	for (i = 0; i <= 9; i++) { //fix 1'234'567		autoCorrectFromTo('′' + i, '\ + i, 2);	}	autoCorrectFromTo(/\D(')$/, '’', 1, VISUAL);	autoCorrectFromTo(/[^0-9'](')$/, '’', 1, SOURCE); //italic/bold syntax	autoCorrectFromTo(/([′’]\')$/, '\'\'', 2, SOURCE); //fix italic/bold syntax	autoCorrectFromTo(/\d(")$/, '″', 1, VISUAL);	autoCorrectFromTo(/(?:^|=\s*"[^"]*")[^=]*(?:=\s*(?:[^" ]|"[^"]*")[^=]*)*\d(")$/, '″', 1, SOURCE); //not in attributes //(?:^|=\s*"[^"]*") - anchor at the start of the line or a quoted attribute	//[^=]* - skip chars that aren't equal signs	//=\s*(?:[^" ]|"[^"]*") - equal sign either not followed by quote mark or with complete quoted attribute	//depending on the content language	if (quotes.hasOwnProperty(lang)) {		autoCorrectFromTo(/(?:^|[( \n])(")$/, quotes[lang][0], 1, VISUAL);		autoCorrectFromTo(/(?:^|=\s*"[^"]*")[^=]*(?:=\s*(?:[^" ]|"[^"]*")[^=]*)*(?:^|[( \n])(")$/, quotes[lang][0], 1, SOURCE); autoCorrectFromTo(/[^\d( \n](")$/, quotes[lang][1], 1, VISUAL);		autoCorrectFromTo(/(?:^|=\s*"[^"]*")[^=]*(?:=\s*(?:[^" ]|"[^"]*")[^=]*)*[^\d( \n=](")$/, quotes[lang][1], 1, SOURCE);	}	//depending on the wiki	/*jshint onecase: true*/	switch (wiki) {	case 'dewiki':		autoCorrectFromTo([{type: 'paragraph'}, '=', 'w'], [			{type: 'heading', attributes: {level: 2}},			'W', 'e', 'b', 'l', 'i', 'n', 'k', 's',			{type: '/heading'},			{type: 'paragraph'}		], 2, VISUAL); //actually just for proof of concept	} }

deps = ['ext.visualEditor.core']; if (mw.libs.ve.isWikitextAvailable) { deps.push('ext.visualEditor.mwwikitext'); }

mw.loader.using(deps).then(function {	if (mw.config.get('wgPageContentModel') === 'wikitext') {		//I use VE for JS/CSS, too, don't enable there		initAutoCorrect(mw.config.get('wgContentLanguage'), mw.config.get('wgDBname'));	}	mw.hook('userjs.script-ready.veAutocorrect').fire; });

})(mediaWiki); //