미디어위키:Common.js
참고: 설정을 저장한 후에 바뀐 점을 확인하기 위해서는 브라우저의 캐시를 새로 고쳐야 합니다.
- 파이어폭스 / 사파리: Shift 키를 누르면서 새로 고침을 클릭하거나, Ctrl-F5 또는 Ctrl-R을 입력 (Mac에서는 ⌘-R)
- 구글 크롬: Ctrl-Shift-R키를 입력 (Mac에서는 ⌘-Shift-R)
- 인터넷 익스플로러 / 엣지: Ctrl 키를 누르면서 새로 고침을 클릭하거나, Ctrl-F5를 입력.
- 오페라: Ctrl-F5를 입력.
/* 이 자바스크립트 설정은 모든 문서, 모든 사용자에게 적용됩니다. */
/*<source lang="javascript"><nowiki>*/
/** [[틀:USERNAME]]에서 사용하는 바꿔치기 함수
* 작성자: [[사용자:Peremen]]
*/
function UserNameReplace() {
if (typeof(disableUsernameReplace) != 'undefined' && disableUsernameReplace) return;
if (!document.getElementById('pt-userpage')) return;
$("span.insertusername").each(function(i) {
$(this).text(mw.config.get("wgUserName"))
})
};
$(UserNameReplace);
/** 플러그인이 작동하지 않을 때 나타나는 내용
* js: noPlugin('(이름)');
* html: class="noplugin-(이름)"
* 작성자: [[사용자:Gustmd7410|Gustmd7410]] */
function noPlugin(name) {
$('.noplugin-' + name).each(function() {
$(this).remove();
});
}
// [[미디어위키:common.js]] 미작동시: class="noplugin"
$('.noplugin').each(function() {
$(this).remove();
});
/* window.location.search를 객체 형태로 반환
@param {object} location 획득할 로케이션 객체, 비어있으면 window.location을 참조
원작성자: [[사용자:BANIP|BANIP]]
*/
function geturlSearch(location) {
location = location || window.location;
var result = {};
if(location.search) decodeURIComponent(location.search)
.substring(1)
.split("&")
.map(function(v) { return v.split("=") })
.forEach(function(v) { result[v[0]] = v[1] });
return result;url.hash = encodeURIComponent(hash);
}
/* 객체형태로 된 SearchParam을 받아 string형태로 반환
원작성자: [[사용자:BANIP|BANIP]]
*/
function searchParamToString(searchParamsObj){
return "?" + Object.entries(searchParamsObj).map(function(v){
return v.map(function(v) {
return encodeURIComponent(v);
}).join("=");
}).join("&");
}
/** [[백괴게임:연습장]] 문서 내용 비우기
* 작성자: [[사용자:*devunt]]
*/
$(function() {
if (mw.config.get("wgPageName") != "리버티게임:연습장")
return;
if (document.URL.lastIndexOf("action=edit") != -1) {
if (document.URL.lastIndexOf("fakeaction=clean") == -1)
return;
var dbindex = document.editform.wpTextbox1;
dbindex.value = "<!-- 이 줄은 지우지 마세요 -->{{리버티게임:연습장/안내문}}[["+"분류:리버티게임 도움말]]";
document.editform.wpSummary.value = "연습장 비움";
document.editform.wpSave.click();
return;
}
});
/** [[틀:제목]]에서 사용하는 제목 바꿔치기 함수
* 작성자: [[사용자:Peremen|Peremen]]
*/
/*
function rewriteTitle() {
if (typeof(disableTitleRewrite) != 'undefined' && disableTitleRewrite) return;
if (!document.getElementById('title-meta')) return;
$('h1.firstHeading').each(function(i) {
$(this).html($("#title-meta").html()).css('text-align', $("#title-align").text());
});
}
$(rewriteTitle);
*/
/** 대문의 탭을 "프로젝트"->"대문"으로 바꾸는 함수.
* 작성자: [[사용자:Peremen|Peremen]]
*/
function MainPageRenameNamespaceTab() {
var hasMainPageTab = document.getElementsByClassName("hasMainPageTab");
if (hasMainPageTab[0] !== undefined) {
$('#ca-nstab-project a').text("대문");
}
var title = mw.config.get('wgPageName');
var hasGameListTab = (title == '백괴게임:게임_목록' || title == '백괴게임토론:게임_목록');
if (hasGameListTab) {
$('#ca-nstab-project a').text("게임 목록");
}
$('#ca-nstab-main a').text("게임");
}
$(MainPageRenameNamespaceTab);
/** 임베드 플래시 무비
* 문서에 플래시 파일을 넣을 수 있게 합니다. [[틀:플래시]]를 참고하십시오.
* 원작성자: [[:en:User:Olipro|Olipro]]
*/
// 플래시 사용 중지에 따라 이 기능은 비활성화됩니다.
/*
function useFlash() {
var flashOk;
var contentTempHolder;
$(embedFlashCheck);
}
function embedFlashMovie(flashOk) {
mainbody = document.getElementById('bodyContent');
mainbody.innerHTML = contentTempHolder;
spancheck = document.getElementsByTagName('span');
for (i = 0; i < spancheck.length; i++) {
if (spancheck[i].getAttribute('id') != 'embedFlashDoc') {
continue;
}
obj = spancheck[i].innerHTML.split('@');
flwidth = obj[0];
flheight = obj[1];
flfile = obj[2].replace('fullurl://', 'https://');
showFlash = ' ';
if (flashOk) {
showFlash = '<object width="' + flwidth + '" height="' + flheight + '"';
showFlash += 'classid="clsid:d27cdb6e-ae6d-11cf-96b8-444553540000"';
showFlash += 'codebase="http://fpdownload.macromedia.com/pub/';
showFlash += 'shockwave/cabs/flash/swflash.cab#version=8,0,0,0">';
showFlash += '<param name="movie" value="' + flfile + '" />';
showFlash += '<embed src="' + flfile + '" width="' + flwidth + '" height=';
showFlash += '"' + flheight + '" type="application/x-shockwave-flash" ';
showFlash += 'pluginspage="http://www.macromedia.com/go/getflashplayer" />';
showFlash += '</object>';
} else {
showFlash = '<a class="plainlinks" href="javascript:embedFlashMovie(true)" onClick="embedFlashMovie(true)">' + flfile + '</a> (신뢰하는 경우 보려면 클릭하십시오.)';
}
spancheck[i].innerHTML = showFlash;
spancheck[i].style.display = 'inline';
}
}
function embedFlashCheck() {
if (!document.getElementById('embedFlashDoc')) {
return;
}
mainbody = document.getElementById('bodyContent');
contentTempHolder = mainbody.innerHTML;
if (typeof displayFlashOverride != 'undefined') {
embedFlashMovie(displayFlashOverride);
return;
}
askmessage = '<div align="center" id="askflash">이 게임에는 ';
askmessage += '<a href="/wiki/백괴:플래시" class="plainlinks">플래시</a>가 들어있습니다.<br />';
askmessage += '컴퓨터에 해를 끼칠 수 있으므로 신뢰하는 경우에만 여십시오.<br />';
askmessage += '플래시가 포함된 게임을 보시겠습니까?<br><b> ';
askmessage += '<a href="javascript:embedFlashMovie(true)" ';
askmessage += 'onClick="embedFlashMovie(true)">예</a> | <a ';
askmessage += 'href="https://libertygame.miraheze.org/">아니오</a>';
mainbody.innerHTML = askmessage;
}
$(useFlash);
*/
/* userAgent */
/** source: http://www.gregoryvarghese.com/how-to-get-browser-name-and-version-via-javascript/ **/
function get_browser_info() {
var ua = navigator.userAgent,
tem, M = ua.match(/(opera|chrome|safari|firefox|msie|trident(?=\/))\/?\s*(\d+)/i) || [];
if (/trident/i.test(M[1])) {
tem = /\brv[ :]+(\d+)/g.exec(ua) || [];
return {
name: 'IE ',
version: (tem[1] || '')
};
}
if (M[1] === 'Chrome') {
tem = ua.match(/\bOPR\/(\d+)/)
if (tem != null) {
return {
name: 'Opera',
version: tem[1]
};
}
}
M = M[2] ? [M[1], M[2]] : [navigator.appName, navigator.appVersion, '-?'];
if ((tem = ua.match(/version\/(\d+)/i)) != null) {
M.splice(1, 1, tem[1]);
}
return {
name: M[0],
version: M[1]
};
}
/** DB기능 초기화
* [[틀:DB]]를 사용 가능하게 해 줍니다.
* 원작성자: [[사용자:BANIP|BANIP]]
*/
function enableLocalStorage() {
// 문서 미리보기 상태일 시 종료
var searchParams = geturlSearch(location);
var isNormalMode =
searchParams.action === undefined &&
searchParams.curid === undefined &&
searchParams.oldid === undefined &&
searchParams.direction === undefined &&
searchParams.printable === undefined &&
searchParams.diff === undefined ;
if (!(isNormalMode)) return "";
//플러그인의 모든 키 순회
function forEach(object, callback) {
for (var key in object) {
var variable = object[key];
callback(variable, key);
}
}
function setLocalStorage(parentKey, datas) {
var stringKeys = JSON.stringify(Object.keys(datas));
localStorage.setItem(parentKey + "/__keys__", stringKeys);
forEach(datas, function(v, i) {
if (i === "action") return;
localStorage.setItem(parentKey + "/" + i, v);
});
}
function getLocalStorage(parentKey) {
var datas = {};
var stringKeys = localStorage.getItem(parentKey + "/__keys__");
if (stringKeys === null) return null;
var keys = JSON.parse(stringKeys);
keys.forEach(function(key) {
datas[key] = localStorage.getItem(parentKey + "/" + key);
})
return datas;
}
function clearLocalStorage(parentKey) {
var datas = {};
var stringKeys = localStorage.getItem(parentKey + "/__keys__");
if (stringKeys === null) return null;
var keys = JSON.parse(stringKeys);
keys.forEach(function(key) {
datas[key] = localStorage.removeItem(parentKey + "/" + key);
})
}
function getSearch() {
return geturlSearch();
}
function searchParamToString(searchParamsObj){
var params = "?" + Object.entries(searchParamsObj)
.map(function(v){ return v.join("=") })
.join("&");
return encodeURI(params);
}
function setSearch(datas) {
var searchParams = getSearch();
forEach(datas, function(v, i) {
searchParams[i] = v;
});
location.search = searchParamToString(searchParams);
}
function hasSearch() {
return !(location.search === "");
}
$(".controlLocalStorage").each(function() {
var parentKey = $(this).data("key");
var behavior = $(this).data("behavior");
switch (behavior) {
case "세이브":
if (!hasSearch()) return;
var datas = getSearch();
clearLocalStorage(parentKey);
setLocalStorage(parentKey, datas);
break;
case "로드":
if (hasSearch()) return;
var datas = getLocalStorage(parentKey, datas);
if (datas === null) return;
setSearch(datas);
break;
case "초기화":
clearLocalStorage(parentKey);
break;
}
})
}
$(enableLocalStorage);
/* DB기능 초기화 끝 */
/** [[틀:CGI2]] 변수 구문 해석기
* 작성자: [[사용자:Gustmd7410]]
**/
var CGI2Parser = (function() {
function CGI2Parser(actions) {
// new 키워드 미사용시
if(!(this instanceof CGI2Parser)) {
console.warn("CGI2Parser 객체를 new 키워드 없이 생성했습니다");
return new CGI2Parser(actions);
}
if(typeof actions === "object") this.actions = actions;
else if(actions === undefined) this.actions = {};
else throw new TypeError("생성자 CGI2Parser의 첫번째 변수가 객체가 아닙니다");
}
CGI2Parser.prototype.parse = function parse(origin, params, useStrict) {
var actions = this.actions;
JSON.parse(params.replace(/\,\s*\]/, "]")).forEach(function(command, useStrict) {
var wrapper = Object.entries(command)[0];
var action = actions[wrapper[0]];
var arg = wrapper[1];
if(typeof action === "function") {
origin = actions[wrapper[0]].apply(origin, Array.isArray(arg)? arg : [arg]) || origin;
} else if(!useStrict) {
return;
} else if(action === undefined) {
origin = new TypeError('동작 "' + wrapper[0] + '"이(가) 존재하지 않습니다');
origin.name = "ActionNoExistError";
throw origin;
} else {
origin = new TypeError('동작 "' + wrapper[0] + '"은(는) 유효하지 않는 타입(' + typeof action + ') 입니다');
origin.name = "ActionWrongTypeError";
throw origin;
}
});
return origin;
};
return CGI2Parser;
})();
/* [[틀:CGI2]] 변수 구문 해석기 끝 */
/** [[틀:CGI2|CGI2]]를 사용 가능하게 만드는 jquery 구문
* 원작성자: [[사용자:BANIP|BANIP]]
* 2차 작성자: [[사용자:Gustmd7410|Gustmd7410]]
**/
function useCGI2() {
$(".cgilink").each(function() {
// CGI2의 page속성과 data속성을 가져옴
var page = $(this).data("page").split('#');
var variables = $(this).data("var");
// 가져온 page데이터 속성을 조합해 url인스턴스 생성
var pagename = page.shift() || mw.config.get('wgPageName');
var hash = page.join('#');
var urlstr = window.location.origin;
var url = new URL(urlstr);
var searchParam = geturlSearch();
// 엄격모드 사용여부 결정
if(typeof useCGI2.useStrict !== "boolean") {
useCGI2.useStrict = (searchParam.debug === "true" || searchParam.debug == 1)? true : false;
}
// 가져온 var속성으로 url 인스턴스의 searchparams를 씹고 뜯고 맛보고 즐기고
var enabledKey = null;
try {
searchParam = new CGI2Parser({
set: function(key, value) {
this[key.trim()] = value.trim();
},
"default": function(key, value) {
key = key.trim();
this[key] = this[key] || value.trim();
},
del: function(key) {
delete this[key.trim()];
},
restrict: function(key) {
if(!enabledKey) enabledKey = [];
enabledKey.push(key);
}
}).parse(searchParam, variables, useCGI2.useStrict);
if(enabledKey) Object.keys(searchParam).forEach(function(key) {
if(!enabledKey.includes(key)) delete searchParam[key];
});
} catch(error) {
$(this).html($("<span class='error' />").text(error.message));
return;
}
// url 경로 조정
if(Object.keys(searchParam).length > 0) {
url.pathname = "/w/index.php";
searchParam.title = pagename;
} else url.pathname = "/wiki/" + mw.util.wikiUrlencode(pagename);
url.search = searchParamToString(searchParam);
url.hash = mw.util.escapeIdForLink(hash);
// cgilink에 a태그 추가
var children = $(this).html();
$(this).html("<a href='" + url.href.replace("'", "'") + "'>" + children + "</a>");
});
}
/*
true = 항상 엄격모드
null = 디버그 모드 (debug=true) 에 엄격모드 자동 전환
false = 엄격모드 사용 안함
*/
useCGI2.useStrict = null;
$(useCGI2);
/* [[틀:CGI2|CGI2]]를 사용 가능하게 만드는 jquery 구문 끝 */
/** mediawiki api를 통해 간단하게 문서들을 수집, 변경하는 함수.
* 플러그인 코어에서 사용하기 위해 만들었습니다.
* 원작성자: [[사용자:BANIP|BANIP]], 수정자: [[사용자:Bd3076|Bd3076]]
* 사용방법
*: var api = MediaWikiAPI(); .changeDocument()
*: api.changeDocument(변경할 문서의 타이틀, 편집 요약, 변경할 문서의 내용) => 문서의 내용을 변경합니다.
*: api.addDocument(변경할 문서의 타이틀, 편집 요약, 추가할 문서의 내용) => 문서에 새로운 내용을 추가합니다.
*: api.getDocument(가져올 문서의 타이틀) => 문서의 모든 텍스트를 읽어옵니다.
*: api.readDocument(가져올 문서의 타이틀) => 문서의 모든 텍스트를 jquery 객체로 읽어옵니다.
* 영 좋지 않은 목적으로 사용 하면 안드로메다 경찰관이 잡아간다!
*/
function MediaWikiAPI() {
var token;
var getToken = function() {
if (token !== undefined) return token;
$.ajax({
url: "/w/api.php?action=query&meta=tokens",
success: function(v, i) {
var datas = JSON.parse($(v).find("pre").text());
token = datas["query"]["tokens"]["csrftoken"];
},
async: false
});
return token;
};
function changeDocument(title, summary, content, isUnReload, minor) {
mw.loader.using( ['mediawiki.util','mediawiki.Title'] ).then( function () {
$.ajax({
url: mw.util.wikiScript("api"),
data: {
format: 'json',
action: 'edit',
title: title,
summary: summary,
text: content,
minor: minor,
token: getToken(),
},
dataType: 'json',
type: 'POST',
success: function(data) {
if (data && data.edit && data.edit.result == 'Success') {
if (!isUnReload) window.location.reload(); // reload page if edit was successful
} else if (data && data.error) {
alert('Error: API returned error code "' + data.error.code + '": ' + data.error.info);
} else {
alert('Error: Unknown result from API.');
}
},
error: function(xhr) {
alert('Error: Request failed.');
}
});
} );
}
function addDocument(title, summary, content, isUnReload, minor) {
originContent = getDocument(title);
changeDocument(title, summary, originContent + content, isUnReload, minor);
}
function getDocument(title) {
function entityDecode(doc) {
return $('<p></p>').html(doc).text();
}
var originContent;
$.ajax({
url: "/w/index.php?title=" + title + "&action=edit",
success: function ajaxSucess(data) {
originContent = $(data).find("textarea").html();
},
async: false
});
return entityDecode(originContent);
}
function readDocument(title) {
var doc;
$.ajax({
url: "/wiki/" + title,
success: function ajaxSucess(data) {
doc = $(data).find("#mw-content-text");
},
async: false
});
return doc;
}
return {
getToken: getToken,
changeDocument: changeDocument,
addDocument: addDocument,
getDocument: getDocument,
readDocument: readDocument,
};
}
/* DB 기능 초기화 끝 */
/** [[틀:플러그인]]을 사용 가능하게 해 줍니다. 사용자의 허락을 맡고 사용자의 commonjs 편집을 허가 할 수 있는 문서입니다.
* 작성자: [[사용자:BANIP|BANIP]]
* [[백괴게임:관리자 요청/2018년 1월]]에서 BANIP님 요청으로 퍼왔습니다.
*/
function pluginCore() {
// 사용자의 commonjs의 문서 이름을 획득
var commonjs = "사용자:" + mw.config.get("wgUserName") + "/common.js";
var plugins = {},
docPlugins = {},
uninstalledPlugins = {},
unupdatedPlugins = {};
var preloadedplugins = [],
needPlugins = [];
var api = MediaWikiAPI();
var jsdoc = api.getDocument(commonjs);
//commonjs에서 특정 플러그인 제거
function removePluginByDoc(pluginTitle, doc) {
var reg = new RegExp("\\/\\*\\* 플러그인 " + pluginTitle + "([\\s\\S]*)\\/\\* " + pluginTitle + " 끝 \\*\\/", "g");
doc = doc.replace(reg, "");
return doc
}
// 플러그인이 비어있는지 확인
function isPluginsEmpty(plugins) {
return Object.keys(plugins).length === 0;
}
//플러그인의 모든 키 순회
function forEach(object, callback) {
for (var key in object) {
var variable = object[key];
callback(variable, key);
}
}
// 문서에서 사용하는 플러그인들을 체크합니다. use-script클래스를 가진 모든 돔 요소를 조사하고
// 그 돔에 내장된 플러그인 데이터를 docPlugins에 추가합니다.
var checkDocPlugin = (function(docPlugins) {
function getPluginData($this) {
return {
name: $this.attr("data-name"), // 플러그인 이름
descript: $this.attr("data-descript"), // 플러그인 내용
version: $this.attr("data-version"), // 플러그인 이름
local: ($this.attr("data-local") === "true") ? true : false,
creat: $this.attr("data-creat"),
state: $this.attr("data-state"),
link: $this.attr("data-link"),
executable: $this.attr("data-executable") === "true" ? true : false,
};
}
function getAllPluginsName(plugins) {
var pluginNames = [];
forEach(plugins, function(plugin) {
var pluginName = plugin.name;
pluginNames.push(pluginName);
})
return pluginNames;
}
var loadAllPlugins = (function(docPlugins) {
$(".use-script").each(function() {
const plugin = getPluginData($(this));
docPlugins[plugin.name] = plugin;
})
})(docPlugins)
var loadAllPlugins = (function(docPlugins) {
if (!isPluginsEmpty(docPlugins)) {
var subTitle = " " + getAllPluginsName(docPlugins).join(", ") + " 플러그인 가동중";
$("#siteSub").text(function(i, v) {
return v + subTitle
});
}
})(docPlugins)
})(docPlugins);
// 사용자가 가지고 있는 플러그인들을 체크합니다.
var checkHavePlugin = (function() {
function getUserPlugins(jsdoc) {
var userplugins = [];
// plugins.---가 있는지 체크하는 정규식
var pluginreg = /JSON \=\> ([\S]+) = (\{.*\})/g;
var nameMatch = pluginreg.exec(jsdoc);
while (nameMatch) {
userplugins.push(JSON.parse(nameMatch[2]));
nameMatch = pluginreg.exec(jsdoc);
}
return userplugins;
}
function isSamePlugin(pluginFirst, pluginSecond) {
return pluginFirst.name == pluginSecond.name
}
function isSameVersionPlugin(pluginFirst, plugiSecond) {
return pluginFirst.version == plugiSecond.version
}
function addNeedPlugins(targetPlugins) {
//global docPlugins, needPlugins
for (var key in targetPlugins) {
var pluginName = docPlugins[key].name;
needPlugins.push(pluginName);
}
}
if (!isPluginsEmpty(docPlugins)) {
preloadedplugins = getUserPlugins(jsdoc);
forEach(docPlugins, function(docplugin) {
var isHavePlugin = false;
forEach(preloadedplugins, function(myplugin) {
if (!isSamePlugin(docplugin, myplugin)) return;
if (!isSameVersionPlugin(docplugin, myplugin)) {
unupdatedPlugins[docplugin.name] = docplugin;
}
isHavePlugin = true;
});
if (!isHavePlugin) {
uninstalledPlugins[docplugin.name] = docplugin;
}
});
addNeedPlugins(uninstalledPlugins);
addNeedPlugins(unupdatedPlugins);
}
})();
function onPluginInstall() {
function getPluginCode(plugin) {
// html로 구성된 코드를 텍스트로
function entityDecode(doc) {
return $('<p></p>').html(doc).text();
}
function getDocHead(plugin) {
var docHead = "";
var toJSONPlugin = Object.assign({}, plugin);
toJSONPlugin.code = undefined;
toJSONPlugin.link = undefined;
docHead += "\n"
docHead += "\n/** 플러그인 " + plugin["name"] + "***************************\n";
docHead += "* " + plugin["descript"] + "\n";
docHead += "* 버전 => " + plugin["version"] + "\n";
docHead += "* 작성자 : [[사용자:" + plugin["creat"] + "|" + plugin["creat"] + "]] \n";
docHead += "* JSON => " + plugin["name"] + " = " + JSON.stringify(toJSONPlugin) + "; \n";
docHead += "*/ \n";
docHead += "function plugin_" + plugin["name"] + "(){\n";
if (plugin.local) docHead += " if($(\"[data-name='" + plugin["name"] + "']\").length >= 1){\n";
return docHead;
}
function getDocFoot(plugin) {
var docFoot = "";
if (plugin.local) docFoot += "\n }\n";
docFoot += "\n}\n";
if (plugin.executable) docFoot += "$( plugin_" + plugin["name"] + " );\n";
docFoot += "/* " + plugin["name"] + " 끝 */\n\n";
return docFoot;
}
var docHead = getDocHead(plugin),
docFoot = getDocFoot(plugin);
return entityDecode(docHead + plugin["code"] + docFoot);
}
$(".install-button").text("설치중..");
$(".install-button").off("click");
var doc = "";
forEach(needPlugins, function(pluginName) {
var plugin = docPlugins[pluginName];
jsdoc = removePluginByDoc(pluginName, jsdoc);
doc += getPluginCode(plugin);
});
api.changeDocument(commonjs, "플러그인 " + needPlugins + "설치", jsdoc + doc);
}
var checkinstalledPlugin = function() {
function appendBox(plugin, status) {
var pluginName = plugin.name;
var box = $(".cloneable.p-box").clone().removeClass("cloneable");
var code = api.readDocument(plugin.state).find("pre.script").html();
docPlugins[pluginName].code = code;
box.find(".p-status").html(status);
box.find(".p-code").html(code.replace(/\s{1,}$/, ""));
box.find(".p-name").text(pluginName);
box.find(".p-descript").text(plugin["descript"]);
if (status == "버전업") {
var thisVersion;
for (var key in preloadedplugins) {
if (preloadedplugins[key].name == plugin["name"]) {
thisVersion = preloadedplugins[key].version;
}
}
box.find(".p-version").text(thisVersion + " => " + plugin["version"]);
} else {
box.find(".p-version").text(plugin["version"]);
}
box.find(".p-local").text(plugin["local"] == true ? "일부 문서만" : "문서 전체");
box.find(".p-creat").text(plugin["creat"]);
$.ajax({
url: "/w/api.php?action=query&prop=revisions&rvdir=older&titles=" + plugin.state,
success: function(v, i) {
var datas = JSON.parse($(v).find("pre").text());
var titleKey = Object.keys(datas["query"]["pages"])[0];
var lastModified = datas["query"]["pages"][titleKey]["revisions"][0]["user"] + "(" + datas["query"]["pages"][titleKey]["revisions"][0]["timestamp"] + ")";
box.find(".p-last").text(lastModified);
},
async: false
})
$(".box-article").append(box);
}
if (isPluginsEmpty(docPlugins) || (isPluginsEmpty(unupdatedPlugins) && isPluginsEmpty(uninstalledPlugins))) return;
var doc = $("#mw-content-text");
var setupMeta = api.readDocument("틀:플러그인/setup");
doc.html(setupMeta);
forEach(uninstalledPlugins, function(uninstalledPlugin) {
appendBox(uninstalledPlugin, "설치");
});
forEach(unupdatedPlugins, function(unupdatedPlugin) {
appendBox(unupdatedPlugin, "버전업");
});
$(".install-button").on("click", onPluginInstall);
}
var showPluginTemplet = (function() {
if (isPluginsEmpty(needPlugins)) {
return;
}
if ($(".plugin-install").length >= 1) {
$(".plugin-install").eq(0).closest("table").show();
$(".plugin-name").eq(0).text(needPlugins);
$(".plugin-install").on("click", checkinstalledPlugin);
} else {
checkinstalledPlugin();
}
})();
}
$(pluginCore)
/** paramtest 함수
* [[틀:CGI2|CGI2]] 등에 적용되는 searchParams 메소드 지원 여부를 판단하는 함수
* 작성자: [[사용자:Manymaster|manymaster]]
*/
function paramtest() {
var test_code;
var Params = new URL(document.location).searchParams;
if (Params === undefined) {
test_code = 0;
} else {
test_code = 1;
}
return test_code;
}
/** paraminfo 함수
* paramtest의 부속 함수로 searchParams 메소드 지원시 지정한 메시지를 숨길 수 있게 해주는 함수
* 메시지는 searchparam_test 클래스로 지정하여 숨길 수 있습니다. */
function paraminfo() {
var test_code = paramtest();
if (test_code == 0) {
return;
} else {
for (var i = 0; i < document.getElementsByClassName("searchparam_test").length; i++) {
document.getElementsByClassName("searchparam_test")[i].style.display = "none";
}
}
}
$(paraminfo);
/* paramtest 및 부속 함수 끝 */
/** [[틀:편집불가]] 재 리뉴얼용 함수
* [[틀:편집불가]]의 브라우저 및 모니터 차별, 3대 원칙 위반 가능 요소 포함 등으로 리뉴얼을 했으나, 리뉴얼한 틀을 소화 못하는 게임이 많아보이는 관계로 재 리뉴얼 합니다.
* 작성자: [[사용자:Manymaster|manymaster]]
*/
function editprevent() {
var caprevent = document.getElementsByClassName("edit-prevent");
var cahisprevent = document.getElementsByClassName("history-prevent");
if (caprevent[0] === undefined || caprevent[0] === null) {
return;
} else {
if (cahisprevent[0] === undefined || cahisprevent[0] === null) {
cahisprevent = document.getElementsByClassName("edit-prevent");
}
var caedit = document.getElementById('ca-edit');
var cahistory = document.getElementById('ca-history');
var caviewsource = document.getElementById('ca-viewsource');
if (caedit !== null && caedit !== undefined){
caedit.innerHTML = caprevent[0].innerHTML;
cahistory.innerHTML = cahisprevent[0].innerHTML;
} else {
caviewsource.innerHTML = caprevent[0].innerHTML;
cahistory.innerHTML = cahisprevent[0].innerHTML;
}
}
return;
}
$( editprevent );
/* [[틀:편집불가]] 재 리뉴얼용 함수 끝 */
/** 스크립트의 함수를 실행시키는 링크 만들기
* $('(객체)').each(function() {
scriptLink(this);
$(this).click(function () {
(함수)
});
});
* 작성자: [[사용자:Gustmd7410|Gustmd7410]] */
function scriptLink(element) {
$(element).html('<a>' + $(element).html() + '</a>');
}
/** [[틀:고급 넘겨주기]]에서 사용하는 넘겨주기 함수
* id="advredirect" data-url="(문서명)"
* 작성자: [[사용자:Gustmd7410|Gustmd7410]] */
$('#advredirect').each(function() {
location.replace(location.origin + $(this).data('url'));
});
/** [[틀:비밀링크]]에서 사용하는 리다이렉트 링크 함수
* class="clearlink" data-url="(문서명)"
* 작성자: [[사용자:Gustmd7410|Gustmd7410]] */
$('.clearlink').each(function() {
scriptLink(this);
$(this).click(function() {
location.replace(location.origin + $(this).data('url'));
});
});
/** [[틀:뒤로]], [[틀:새로고침]], [[틀:앞으로]]에서 사용하는 방문기록 이동 함수
* class="historygo" data-url="(문서명)"
* 작성자: [[사용자:Gustmd7410|Gustmd7410]] */
$('.historygo').each(function() {
scriptLink(this);
$(this).click(function() {
history.go($(this).data('page'));
});
});
/** [[특수:올리기]]에 파일 정보 틀 자동 로드
* [[w:특수:고유링크/20640234]] 이 스크립트는 위키백과 펌이므로, 위키백과 라이선스인 CCL BY-SA가 적용됩니다.
*/
function uploadPreload() {
// 새 버전 올리기일 때 동작 안 함
if (mw.util.getParamValue('wpForReUpload') !== null) return;
// 설명란이 있고 비어있을 때 내용 변경
var desc = document.getElementById('wpUploadDescription');
if(desc !== null && desc.value === '' ) {
desc.value = '{\{파일 정보\n|설명 = \n|출처 = \n|날짜 = \n}}\n';
}
}
jQuery( document ).ready(uploadPreload);
/* [[특수:올리기]]에 파일 정보 틀 자동 로드 끝 */
/** [[틀:로고 바꾸기]]용 함수 V 1.1
* 작성자: [[사용자:Manymaster|manymaster]],
* 1.1 업데이트: [[사용자:BANIP|BANIP]]
*/
function logochange() {
// 허용 확장자 및 url 패턴
var allwedURLPattern = ["i.uncyclopedia.kr/game/","i.uncyclopedia.kr/pedia/","upload.wikimedia.org/wikipedia/commons/"]
var allowedExt = ["gif","png","jpg","jpeg","svg"]
const logoElement = document.getElementsByClassName("changelogo123");
/* .changelogo 요소가 없으면 종료 */
if (logoElement.length === 0) {
return;
}
var logoTest = logoElement[0].innerHTML.toLowerCase();
//이미지 url이 주어진 조건에 맞는지 검사
var isSafeURL = allwedURLPattern.some( function(middleURL){
var reg = new RegExp("//" + middleURL)
return ( logoTest.match(reg) != null)
})
var isSafeExt = allowedExt.some( function(ext){
var reg = new RegExp("\." + ext + "$")
return ( logoTest.match(reg) != null)
})
// URL패턴과 확장자의 조건이 맞지 않으면 종료
if ( !(isSafeURL && isSafeExt) ) {
return;
}
/* 로고 교체 */
var orglogoElement = document.querySelector("#p-logo a");
orglogoElement.style.backgroundImage = "url('" + logoElement[0].innerHTML + "')";
/* 사이즈 교체 */
var widthElement = document.querySelector(".changelogowidth");
widthElement.innerHTML = widthElement === null ? "160px" : widthElement.innerHTML;
var heightElement = document.querySelector(".changelogoheight");
heightElement.innerHTML = heightElement === null ? "160px" : heightElement.innerHTML;
orglogoElement.style.backgroundSize = widthElement.innerHTML + " " + heightElement.innerHTML;
}
$(logochange);
/* [[틀:로고 바꾸기]]용 함수 끝 */
/**
* [[백괴게임:댸문]]문서의 일부 링크를 낚시문서로 바꿔치기
* 원작성자: [[사용자:BANIP|BANIP]]
*/
$(function(){
var gate = document.getElementsByClassName("fakegate");
if (gate[0] === undefined || gate[0] === null) {
return;
} else{
var targetLink = "https://libertygame.miraheze.org/wiki/"+gate[0].innerHTML;
$("#bodyContent a").attr("href",targetLink);
}
})
/* [[백괴게임:댸문]]문서의 일부 링크를 낚시문서로 바꿔치기 끝 */
/**
* pluginX Core
* pluginX 시스템이 제대로 돌아가게 해 줍니다.
* 작성자: [[사용자:Bd3076|Bd3076]]
*/
function pluginXCore() {
var api = MediaWikiAPI();
var ipUser = false;
if(mw.config.get("wgUserName") === null) ipUser = true;
var script_list = [];
var pluginExist = false;
var neededPluginExist = false;
var html_before;
var jsonDoc = "사용자:" + mw.config.get("wgUserName") + "/pluginX.json";
var jsonData = JSON.parse(api.getDocument(jsonDoc));
/// 플러그인의 정보가 담긴 데이터를 만듭니다.
var generateScriptData = function(_url, _name, _creator, _doc, _script, _revid){
return {
url: _url,
name: _name,
creator: _creator,
doc: _doc,
script: _script,
revid: _revid
};
};
/// 플러그인 목록을 만들어서 script_list[]에 담습니다.
var getPluginList = function(){
$(".c_pluginX").each(function() {
pluginExist = true;
var url = $(this).attr('data-url');
var name = $(this).attr('data-name');
var creator = $(this).attr('data-creator');
var doc = $(this).attr('data-doc');
var revid = $(this).attr('data-revid');
var script = api.getDocument(doc);
script_list.push(generateScriptData(url, name, creator, doc, script, revid));
if(jsonData[doc] === undefined || jsonData[doc] !== revid){
console.log(name);
neededPluginExist = true;
}
});
};
/// 플러그인을 실행합니다.
var executePlugins = function(){
script_list.forEach(function(data){
var link = data.url;
var revid = data.revid;
var doc = data.doc;
if(neededPluginExist){
jsonData[doc] = revid;
}
$.getScript(link);
});
///자동 인증된 사용자가 플러그인을 실행할 경우 json을 갱신합니다.
var userGroups = mw.config.get('wgUserGroups');
var autocheck = 0;
if (userGroups) {
for (var i = 0; i < userGroups.length; i++) {
if (userGroups[i] === 'autoconfirmed') {
autocheck++;
}
}
}
if(neededPluginExist && !(autocheck == 0) ){
api.changeDocument(jsonDoc, "pluginX - 새로운 플러그인", JSON.stringify(jsonData));
}
};
/// 플러그인을 실행하지 않습니다.
var doNotExecutePlugins = function(){
document.getElementById('mw-content-text').innerHTML = html_before;
};
/// 알림 창을 만듭니다.
var showWindow = function(){
html_before = document.getElementById('mw-content-text').innerHTML;
$('#mw-content-text').html(api.readDocument("틀:PluginX/setup"));
var script = "";
script_list.forEach(function(data){
var addingCode;
addingCode = '<div class="px-code"><pre>';
addingCode = addingCode.concat(((data.script.replace(/&/g, '&')).replace(/</g, '<')).replace(/>/g, '>'));
addingCode = addingCode.concat('</pre> </div> <div class="px-codeinfo"> <ul> <li> 플러그인 이름: ');
addingCode = addingCode.concat(data.name);
addingCode = addingCode.concat('</li> <li> 플러그인 제작자: ');
addingCode = addingCode.concat(data.creator);
addingCode = addingCode.concat('</li> </ul> </div>');
// 위험 코드 탐지 시작
var pattern;
var nscode = data.script.replace(/\r?\n|\r/g, ' ');
// 패턴 1. document.innerHTML 사용 (위험도: 심각)
pattern = new RegExp("^.*document *\. *innerHTML.*$");
if(pattern.test(nscode)){
addingCode = addingCode.concat('<div class="px-critical">이 플러그인은 문서 열람 시 지장을 줄 수 있습니다.<br>플러그인 제작자를 신뢰할 수 있는 경우에만 실행하시기 바랍니다.</div>');
}
// 패턴 2. document.write 사용 (위험도: 심각)
pattern = new RegExp("^.*document *\. *write.*$");
if(pattern.test(nscode)){
addingCode = addingCode.concat('<div class="px-critical">이 플러그인은 문서 내용을 왜곡시킬 수 있습니다.<br>플러그인 제작자를 신뢰할 수 있는 경우에만 실행하시기 바랍니다.</div>');
}
// 패턴 3. "wgUserName" 사용 (위험도: 안내)
pattern = new RegExp('^.*"wgUserName".*$');
if(pattern.test(nscode)){
addingCode = addingCode.concat('<div class="px-notice">이 플러그인은 당신의 사용자 이름을 수집합니다.<br>이를 원치 않으시면 플러그인을 실행하지 마시기 바랍니다.</div>');
}
//패턴 4. MediaWikiAPI.changeDocument 사용(위험도: 경고)
pattern = new RegExp('^.*MediaWikiAPI.*changeDocument.*$');
if(pattern.test(nscode)){
addingCode = addingCode.concat('<div class="px-warning">이 플러그인은 다른 문서를 편집합니다.<br>이 게임이 계정 생성형 게임일 가능성이 높습니다.<br>플러그인 제작자를 신뢰할 수 있는 경우에만 실행하시기 바랍니다.</div>');
}
script += addingCode;
});
document.getElementById('px-script').innerHTML = script;
$('#px-button').on('click', executePlugins);
$('#px-button2').on('click', doNotExecutePlugins);
};
getPluginList();
if(pluginExist === false) return;
if(neededPluginExist === false){
executePlugins();
return;
}
else{
showWindow();
return;
}
}
$(pluginXCore);
/* pluginX Core 끝 */
/** [[틀:SCGI]]에서 사용하는 링크 리다이렉트 함수
* class="scgi-use"
* 작성자: [[사용자:Gustmd7410|Gustmd7410]]
**/
$(function useSCGI() {
if(!URLSearchParams) return;
$('.scgi-use a').each(function() {
var href = new URL(this.href);
var params = new URLSearchParams(location.search);
if(
location.host === href.host && (
location.pathname === '/w/index.php' && params.get('title') ||
location.pathname.startsWith('/wiki/') && location.pathname.replace('/wiki/', '')
) === (
href.pathname === '/w/index.php' && params.searchParams.get('title') ||
href.pathname.startsWith('/wiki/') && href.pathname.replace('/wiki/', '')
) && params.get('action') === href.searchParams.get('action')
) $(this).click(function(event) {
event.preventDefault();
location.replace(event.currentTarget.href);
});
});
});
/* [[틀:SCGI]]에서 사용하는 링크 리다이렉트 함수 끝 */
/** 편집 저장시 다른 문서나 CGI로 넘겨주기
* ?action=edit&redirectquery=(params)
* 작성자: [[사용자:Gustmd7410|Gustmd7410]]
**/
$(function() {
// 현재 URL 파라미터
var params;
// URLSearchParams 호환시
if(URLSearchParams) params = new URLSearchParams(location.search);
// 비호환시 geturlSearch() 사용
else {
// Map 호환시
if(Map) params = new Map(Object.entries(geturlSearch()));
// 비호환시 mw.Map 사용
else {
params = new mw.Map();
params.values = geturlSearch();
params.has = params.exists;
}
}
// 편집창에서 redirectquery 파라미터가 있을때
if(params.has('redirectquery')) {
// 편집 폼에 wpExtraQueryRedirect 파라미터 input 요소 추가
$('#editform').append($('<input />', {
type: 'hidden',
name: 'wpExtraQueryRedirect',
value: params.get('redirectquery')
}));
}
});
/* 편집 저장시 다른 문서나 CGI로 넘겨주기 끝 */
/** 기여 확인용 플러그인
* 작성자: [[사:Bd3076|Bd3076]]
*/
function enoughEdit(){
function compareEditCount(number, id1, id2){
var editCount = mw.config.get('wgUserEditCount');
if(editCount < number){
document.getElementById(id1).style.display = "block";
}
else{
document.getElementById(id2).style.display = "block";
}
}
$('.editCompare').each(function(){
var num = $(this).attr("data-num");
var enough = $(this).attr("data-id1");
var nenough = $(this).attr("data-id2");
compareEditCount(num, enough, nenough);
});
}
$(enoughEdit);
/* 기여 확인용 플러그인 끝 */
/** 상위 문서 링크 바꿔치기
* id="setsub"
* 작성자: [[사용자:Gustmd7410|Gustmd7410]]
**/
function changeContentSub() {
var newsub = document.getElementById('setsub');
if(newsub) {
document.querySelector('#contentSub').innerHTML = newsub.innerHTML;
newsub.remove();
}
}
$(changeContentSub);
/* 상위 문서 링크 바꿔치기 끝 */
/** [[틀:자동저장]]용 문서 미리 비워놓기
* 원출처: [[틀:자동저장/플러그인]]
* 비 자동 인증된 사용자가 자동저장 겸용 문서에서 복붙을 할 때
* 문서를 덮어씌우지 않고 밑에 복붙을 하는 상황을 막기 위한 플러그인입니다.
*/
function nonautosaveready() {
/* autosave 편집모드가 아닐 경우 플러그인 종료 */
var searchParams = geturlSearch(location);
var isEditMode = searchParams.action === "edit";
var isAutosaveMode = searchParams.autosave === "1";
if (!(isEditMode && isAutosaveMode)) return "";
/* 자동 저장하기에 안전한 네임스페이스가 아닌 경우 플러그인 종료 */
var safeNameSpace = [""];
var thisNamespaceNumber = mw.config.get("wgNamespaceNumber");
var nameSpaceIds = mw.config.get("wgNamespaceIds");
var isSafeNameSpace = safeNameSpace
.map(function (namespace) { return nameSpaceIds[namespace]; })
.some(function (nsNumber) { return nsNumber == thisNamespaceNumber; });
if (!(isSafeNameSpace)) return "";
/* 자동 인증된 사용자가 일 경우 플러그인 종료 */
var userGroups = mw.config.get('wgUserGroups');
var autocheck = 0;
if (userGroups) {
for (var i = 0; i < userGroups.length; i++) {
if (userGroups[i] === 'autoconfirmed') {
autocheck++;
}
}
}
if (autocheck != 0) return "";
/* 미리 비워놓기 */
var savetemp = document.editform.wpTextbox1;
savetemp.value = "";
return;
}
$(nonautosaveready);
/* [[틀:자동저장]]용 문서 미리 비워놓기 끝 */