Участник:Ak5271/monobook.js

Материал из свободной русской энциклопедии «Традиция»
Перейти к навигации Перейти к поиску

Замечание: Чтобы после сохранения вступили в силу изменения стилей, перезагрузите файл //traditio.wiki/w/load.php?debug=false&lang=ru&modules=site&only=styles&skin=vector&*, если используете скин Vector, или //traditio.wiki/w/load.php?debug=false&lang=ru&modules=site&only=styles&skin=common&*, если используете скин Common.

Чтобы вступили в силу изменения скриптов, перезагрузите файл //traditio.wiki/w/load.php?debug=false&lang=ru&modules=site&only=scripts&skin=vector&*, если используете скин Vector, или //traditio.wiki/w/load.php?debug=false&lang=ru&modules=site&only=scripts&skin=common&*, если используете скин Common.

Гаджеты и импортируемые скрипты загружаются отдельными файлами.

//Скрипт проверяет правильность закрытия тегов.
//Автор: X-romix
 
if (wgAction == 'edit' || wgAction == 'submit')
addOnloadHook(function(){
	var wpSave = document.getElementById('wpSave');
	if (!wpSave) return;
	addHandler(wpSave, 'click', XRomix_CheckTagsHandler);
});	
 
 
function XRomix_CheckTagsHandler(e){
	var xSelectionStart=0;
	var xSelectionEnd=0;
	var wpTextbox1 = document.editform.wpTextbox1;
 
	var isCancel=false;
	var text=document.editform.wpTextbox1.value;
 
	var isCancel=!XRomix_CheckTags(text);
	if(isCancel){
		setSelectionRange(wpTextbox1, xSelectionStart, xSelectionEnd);
		isCancel= !window.confirm("Имеются ошибки форматирования. Всё равно сохранить?");
	}else{
		setRedWindow(""); //Очищаем красное окно, если оно было
	}
	if (isCancel){ //отменить нажатие кнопки
 
		e = e || window.event //из-за различий в IE и стандартных браузерах
		if (e.preventDefault) e.preventDefault(); else e.returnValue = false //остановить действие, снова по-разному
		return false //на всякий случай
	}
 
 
 
	//Выводит красное окно предупреждения
	function setRedWindow(res){
 
		var w = document.getElementById('XRomix_editpage_CheckTags');
 
		if (res!=""){
			var wpSummary = document.getElementById('wpSummary')
			if (!wpSummary) return
 
			var w = document.getElementById('XRomix_editpage_CheckTags');
			if(!w){ 
				w = document.createElement('span')
				w.id = 'XRomix_editpage_CheckTags'
				wpSummary.parentNode.insertBefore(w, wpSummary.nextSibling);
			}
			w.innerHTML = '<div style="padding:10px; margin:5px; background:#FF8080; border:1px solid red;">'+
			'Имеются незакрытые (или неправильно закрытые) элементы HTML или вики-разметки. ' + res +' '+ 
		    ' (<a href="' + wgArticlePath.replace(/\$1/, 'Википедия:Как править статьи') +
		    '" title="(ссылка откроется в новом окне)" target=_blank>подробнее&nbsp;↗</a>)</div>';
 
 
		}else{
	        if(w) w.innerHTML=''; //Если нет ошибки, то очищаем  	
		}
 
 
	}
 
	//////////////////////////////////////
	//генерирует строку из пробелов указанной длины
	function generateSpaces(len){
	    var s1="                ";
		while(s1.length<len){
			s1+=s1;
		}
		return s1.substr(0,len);
	}
 
 
	//////////////////////////////////////
	//Проверяет теги
	function XRomix_CheckTags(text){
 
			//////////////////////////////////////
			//Заменяет текст между открывающим и закрывающим тегами на пробелы
			function replaceTags(tag1, tag2){
				while(1==1){
					var p=txt.search(tag1);
					if(p==-1) break;
					var p1=txt.indexOf(tag2,p);
					if(p1==-1) { //ошибка, закрывающий тег не найден
						setRedWindow('Не закрыт элемент '+htmlEncode(tag1)+'.');
						xSelectionStart=p;
						xSelectionEnd=p+tag2.length+1;
						return false;
					}
					var w1=generateSpaces(p1-p+tag2.length); 
					var left=txt.substr(0, p);
					var right=txt.substr(p1+tag2.length);
					txt=left+w1+right;
				}	
				return true;
 
			}
 
 
			//////////////////////////////////////
			//Заменяет тег на пробелы
			function replace1Tag(tag1){
				var p=txt.indexOf(tag1);
				if(p==-1) return;
				var w1=generateSpaces(tag1.length); 
				var left=txt.substr(0, p);
				var right=txt.substr(p+tag1.length);
				txt=left+w1+right;
			}
 
 
 
		var ok=0;
		if (document.URL.match(/\.js&action=(edit|submit)/)){
		  return true; //JavaScript не проверяем
		}else if (document.URL.match(/\.css&action=(edit|submit)/)){
		  return true; //CSS не проверяем
		}else if (wgTitle.match (/(Шаблон|Template)\:/)){
		  return true; //Шаблоны не проверяем
		}else if ('code'.replace(/d/g, 'r') != 'core'){  //Проверяем, поддерживает ли браузер регулярные выражения (RegExp)	
		  return true;
		}
 
		var wpTextbox1 = document.editform.wpTextbox1;
		if(!wpTextbox1) return true;
 
		var txt = wpTextbox1.value;
 
		var ok=replaceTags(/<nowiki>/, "</nowiki>");
		if(!ok) return false;
		var ok=replaceTags(/<\!\-\-/, "-->");
		if(!ok) return false;
		var ok=replaceTags(/<math>/, "</math>");
		if(!ok) return false;
		var ok=replaceTags(/<source[\s>]/, "</source>");
		if(!ok) return false;
		var ok=replaceTags(/<pre[\s>]/, "</pre>");
		if(!ok) return false;
 
		var arrPos = new Array();
		var arrTags= new Array();
 
 
		var arr = txt.match(/(<[\/]?[A-Za-z][^>]*>|\[\[|\]\]|\{\{|\}\})/g);
		if(arr==null) return true; //Нет тегов для проверки - возврат
		if(arr){
			for(var i=0; i<arr.length; i++){
				var w=arr[i];
				var pos=txt.indexOf(w);
				//Запоминаем позицию и текст тега
				arrPos.push(pos);
				arrTags.push(w);
				//Заменяем тег на пробелы
				replace1Tag(w);
			}
		}
 
 
		var arrStackTags = new Array();
		var arrStackPos = new Array();
 
 
		for(var i=0; i<arrTags.length; i++){
			var TagName=arrTags[i];
			var TagPos=arrPos[i];
 
			if (TagName.search(/(\/[\s]*>|<hr>|<br>)/) >=0 ){  // <тег/>
				continue; //пропускаем такие теги, поскольку они не требуют закрытия
			}else if(TagName.search(/<[a-zA-Z][^>]*>/) >=0){ 
				//открывающий <тег ...>
 
				//помещаем тег и его позицию в стек
				arrStackTags.push(TagName); 
				arrStackPos.push(TagPos); 
 
			}else if(TagName.search(/<\/[^>]+>/) >=0){ 
				//Закрывающий </тег>
 
				var TagNameN=TagName.replace(/[<>\/]/g, "");
				TagNameN=TagNameN.toLowerCase(); //Нормализованное имя тега - без угловых скобок и /
 
				if (arrStackTags.length==0){
 
					setRedWindow('Неожиданный закрывающий тег '+htmlEncode(TagName)+'.')
					xSelectionStart=TagPos;
					xSelectionEnd=TagPos+TagName.length;
 
					return false;
				}else{
 
					var TagName2=arrStackTags.pop();
					var TagPos2=arrStackPos.pop();
 
					var TagName2N=TagName2.replace(/[\s][^>]*/, ""); //убираем все после первого пробела
					TagName2N=TagName2N.replace(/[<>\/]/g, "");//убираем </>
					TagName2N=TagName2N.toLowerCase();
					if(TagNameN!=TagName2N){
						setRedWindow('Неожиданный закрывающий тег '+htmlEncode(TagName)+' после открывающего тега '+htmlEncode(TagName2)+'.');
						xSelectionStart=TagPos;
						xSelectionEnd=TagPos+TagName.length;
 
						return false;
					}
 
 
				}
			}else if(TagName=="[["){ 	
				arrStackTags.push(TagName); 
				arrStackPos.push(TagPos); 
			}else if(TagName=="{{"){ 	
				arrStackTags.push(TagName); 
				arrStackPos.push(TagPos); 
			}else if(TagName=="]]"){ 	
				if (arrStackTags.length==0){
					setRedWindow('Неожиданный закрывающий элемент '+htmlEncode(TagName)+'.');
						xSelectionStart=TagPos;
						xSelectionEnd=TagPos+TagName.length;
 
					return false;
				}else{
 
					var TagName2=arrStackTags.pop();
					var TagPos2=arrStackPos.pop();
					if(TagName2!="[["){
						setRedWindow('Неожиданный закрывающий тег '+htmlEncode(TagName)+' после открывающего тега '+htmlEncode(TagName2)+'.');
						xSelectionStart=TagPos;
						xSelectionEnd=TagPos+TagName.length;
 
						return false;
					}
				}
			}else if(TagName=="}}"){ 	
				if (arrStackTags.length==0){
					setRedWindow('Неожиданный закрывающий элемент '+htmlEncode(TagName)+'.');
					xSelectionStart=TagPos;
					xSelectionEnd=TagPos+TagName.length;
 
					return false;
				}else{
 
					var TagName2=arrStackTags.pop();
					var TagPos2=arrStackPos.pop();
					if(TagName2!="{{"){
						setRedWindow('Неожиданный закрывающий тег '+htmlEncode(TagName)+' после открывающего тега '+htmlEncode(TagName2)+'.');
						xSelectionStart=TagPos;
						xSelectionEnd=TagPos+TagName.length;
 
						return false;
					}
				}
			}
		}//for
		if(arrStackTags.length>0){
			var TagName=arrStackTags.pop()
			var TagPos=arrStackPos.pop();
			setRedWindow('Имеется незакрытый элемент '+htmlEncode(TagName)+'.');
			xSelectionStart=TagPos;
			xSelectionEnd=TagPos+TagName.length;
 
			return false;
		}//if
	        return true; //нет ошибок
	}//function
 
	//подсчитывает концы строк в фрагменте текста
	function countCrlf(str){
		str=""+str;
		var arr=str.match(/\n/g);
		//Теперь массив содержит концы строк - возвращаем его длину
		if (arr) return arr.length;
		return 0;
	}
 
	//Извлекает первую строку (до \n или \r) из строки
	function get1string(text){
		var p=text.indexOf("\n");
		var p1=text.indexOf("\r");
		if(p1!=-1 && p!=-1){
			if(p>p1) p=p1;
		}
		if(p!=-1){
			text=text.substr(0, p);
		}
		return text;
	}
 
	//Браузеро-независимый setSelectionRange - изменяет начало и конец
	//выделенного фрагмента в поле ввода input
	function setSelectionRange(input, start, end){
		if(!input) return;
		if(!input.value) return;
		var text=input.value.substring(start, end);
		text=get1string(text);
 
		if (input.setSelectionRange) {//Mozilla/Opera
			//Попытаемся спозиционировать курсор на нужный текст
 
			if (self.find) {//Mozilla, в Опере не работает
				input.focus();
				input.setSelectionRange(start, start);	
				var  caseSensitive = false 
				var  backwards = false 
				var  wrapAround = false 
				self.find(text, caseSensitive, backwards, wrapAround);	
			}	
 
			//Выделим диапазон
			input.focus();
			input.setSelectionRange(start, end);
 
 
		}else if (document.selection && document.selection.createRange) { //Internet Explorer
			//IE проглючивает с началом и концом выделенного фрагмента - вносим исправление
			var cnt1=countCrlf(input.value.substring(0, start));
			var cnt2=countCrlf(input.value.substring(start, end));
 
			var range = input.createTextRange();
 
			if(range.findText){
				input.focus();
				range.collapse(true);
				range.moveStart("character", start - cnt1);
				range.moveEnd("character", start - cnt1);
				range.select();
 
				range.findText(text);
				range.collapse(true);
			}
 
			var range = input.createTextRange();
			//Выделяем диапазон в IE
			input.focus();
			range.collapse(true);
			range.moveStart("character", start - cnt1);
			range.moveEnd("character", end - start - cnt2);
			range.select();
 
 
		}	
	}
 
 
 
	//Кодирование спецсимволов HTML
	function htmlEncode(s){
	  s=s.replace(/[\&]/g, "&amp;");
	  s=s.replace(/[<]/g, "&lt;");
	  s=s.replace(/[>]/g, "&gt;");
	  return s;
	}
}
//Форматирует таблицу, скопированную из Excel, по правилам вики-разметки.
//Часть кода позаимствована из http://ru.wikipedia.org/wiki/MediaWiki:Wikificator.js
//Автор: X-romix
 
var XRomix_Tablify_CantWork1 = 'Таблификатор не может работать в вашем браузере.\n\nTablificator cannot work in your browser' // английский текст для тех, кто не видит русские буквы
var XRomix_Tablify_FullText1 = 'Эта кнопка предназначена для форматирования табличного текста, скопированного из табличного редактора (например, из Excel). Чтобы функция заработала, сначала выделите нужный фрагмент текста в окне редактирования.'
 
//Добавляет кнопку
function addTablifikatorButton1(){
	var toolbar = document.getElementById('toolbar')
	var textbox = document.getElementById('wpTextbox1')
	if (!textbox || !toolbar) return
	var i = document.createElement('img')
	i.src = 'http://upload.wikimedia.org/wikipedia/ru/c/c1/Button-tablifikator.PNG'
	i.alt = i.title = 'Таблификатор'
	i.onclick = XRomix_Tablify1
	i.style.cursor = 'pointer'
	toolbar.appendChild(i)
 
} 
 
 
 
//Этот код выполняется в начале.
if (wgAction == 'edit' || wgAction == 'submit'){
  addOnloadHook(addTablifikatorButton1)
}
 
 
//Функция для оформления таблицы
function XRomix_Tablify1(){
 
 //Проверяем, поддерживает ли браузер регулярные выражения (RegExp)	
 if (('code'.replace(/d/g, 'r') != 'core') 
    || (navigator.appName=='Netscape' && navigator.appVersion.substr (0, 1) < 5))
  { alert(XRomix_Tablify_CantWork1); return }
 setWpSummary();
 var txt, hidden = [], hidIdx = 0, wpTextbox1 = document.editform.wpTextbox1
 var winScroll = document.documentElement.scrollTop //remember window scroll
 wpTextbox1.focus()
 
 if (typeof wpTextbox1.selectionStart != 'undefined' 
    && (navigator.productSub > 20031000 || is_safari)) { //Mozilla/Opera/Safari3
 
    var textScroll = wpTextbox1.scrollTop
    var startPos = wpTextbox1.selectionStart
    var endPos = wpTextbox1.selectionEnd
    txt = wpTextbox1.value.substring(startPos, endPos)
    if (txt == '') {alert(XRomix_Tablify_FullText1); return}
    else{
 
	  processText()
      wpTextbox1.value = wpTextbox1.value.substring(0, startPos) + txt + wpTextbox1.value.substring(endPos)
    }
    wpTextbox1.selectionStart = startPos
    wpTextbox1.selectionEnd = startPos + txt.length
    wpTextbox1.scrollTop = textScroll
 
 }else if (document.selection && document.selection.createRange) { //IE
 
   var range = document.selection.createRange()
   txt = range.text
   if (txt == '') {alert(XRomix_Tablify_FullText1); return}
   else{
 
     processText()
	  range.text = txt
     //if (!window.opera) txt = txt.replace(/\r/g,'')
     if (range.moveStart) range.moveStart('character', - txt.length)
     range.select() 
   }
 
 }else // Для браузеров, которые не умеют возвращать выделенный фрагмент, выдаем ошибку
   { alert(XRomix_Tablify_CantWork1); return }
 
 document.documentElement.scrollTop = winScroll // scroll back, for IE/Opera
 
//Здесь производим замену в переменной txt - это отразится на выделенном фрагменте текста 
function processText(){
  var col1hdr=0;
  if (confirm('Вы хотите оформить первую колонку как заголовок?')) col1hdr=1;
 
 
 
  txt = txt.replace(/^\s+|\s+$/g, '')  //Обрезаем пробелы слева и справа
   var arr1=txt.split("\n")
 
   txt='\n{| class="standard"\n'
 
   for (var i=0; i<arr1.length; i++){ 
     txt = txt+"|-\n"
     s1=arr1[i];
	   var arr2=s1.split("\t")
	   for (var j=0; j<arr2.length; j++){
	     var s2=arr2[j];
		 if ((col1hdr==1 && j==0)||i==0){
		   txt = txt+"! "+s2+"\n"
		 }else{
		   txt = txt+"| "+s2+"\n"
		 }  
	   }  
   }  
  txt = txt+"|}"
 
}	
 
  function setWpSummary(){
     var wpSummary = document.getElementById('wpSummary')
	 if(wpSummary){
	    var temp=wpSummary.value;
	    temp=temp.replace(/\/\*.*?\*\// , ""); //комментарии
	    temp=temp.replace(/[\s]*/ , ""); //пробелы
	    if (temp==""){
	       wpSummary.value=wpSummary.value+" - [[User talk:X-romix/tablifikator.js|tablifikator.js]] - таблица из Excel/Calc";
	    }
	 }
  }