// -------------------------------------------------------------------------------
// --- описание класса rButton
// -------------------------------------------------------------------------------
	function rButton(name, type, action, title){ // Команды RE
		this.classType = "button";
		this.name		= name;							// имя команды (имя картинки в директории ./img/re_NAME.gif)
		this.type		= type;							// режим в котором кнопка активна
		this.action	= action;						// функция обработчик
		this.title	= title;						// подпись
		this.button = null							// собственно кнопки как объект
	}
	function rSelect(name, type, action, values, titles){ // Команды RE
		this.classType = "select";
		this.name		= name;							// имя команды (имя картинки в директории ./img/re_NAME.gif)
		this.type		= type;							// режим в котором кнопка активна
		this.action	= action;						// функция обработчик
		this.titles	= titles;						// значения
		this.values	= values;						// подписи
		this.button = null							// собственно кнопки как объект

	}
// -------------------------------------------------------------------------------
// --- описание класса rPanel
// -------------------------------------------------------------------------------
	var orPanel=null;
	function rPanel(){ // Панель инструментов RE
		this.commands = Array( 
			new rButton('inserttable',				rTypeRich,						rActionExtend|rActionText,'Вставить таблицу'),
			new rButton('tableproperties',		rTypeRich,						rActionExtend|rActionObject,'Свойства таблицы'),
			new rButton('bgcolor',						rTypeRich,						rActionExtend|rActionText,'Цвет фона ячейки'),
		new rButton('spacer',rTypeNone),
			new rButton('mergeright',					rTypeRich,						rActionExtend|rActionText,'Объединить ячейку с правой'),
			new rButton('mergedown',					rTypeRich,						rActionExtend|rActionText,'Объединить ячейку с нижней'),
			new rButton('mergenone',					rTypeRich,						rActionExtend|rActionText,'Отменить объединение ячеек'),
		new rButton('spacer',rTypeNone),
			new rButton('insertrow',					rTypeRich,						rActionExtend|rActionText,'Вставить строку'),
			new rButton('deleterow',					rTypeRich,						rActionExtend|rActionText,'Удалить строку'),
			new rButton('insertcol',					rTypeRich,						rActionExtend|rActionText,'Вставить столбец'),
			new rButton('deletecol',					rTypeRich,						rActionExtend|rActionText,'Удалить столбец'),
		new rButton('spacer',rTypeNone),
			new rButton('imageproperties',		rTypeRich,						rActionExtend|rActionObject,'Свойства изображения'),
			new rButton('libraryimages',			rTypeRich|rTypeText,	rActionExtend,'Библиотека картинок'),
		new rButton('spacer',rTypeNone),
			new rButton('libraryfiles',				rTypeRich|rTypeText,	rActionExtend,'Библиотека файлов'),
			new rButton('createlink',					rTypeRich,						rActionExtend|rActionText,'Вставить ссылку'),
		new rButton('spacer',rTypeNone),
			//new rButton('forecolor',					rTypeRich,						rActionExtend|rActionText,'Цвет текста'),
			new rButton('clearformat',				rTypeRich,						rActionExtend|rActionText,'Очистка стилей'),
		new rButton('break',rTypeNone),
			new rButton('bold',								rTypeRich,						rActionBasic,'Полужирный [ctrl + b]'),
			new rButton('italic',							rTypeRich,						rActionBasic,'Курсив [ctrl + i]'),
			new rButton('underline',					rTypeRich,						rActionBasic,'Подчеркнутый [ctrl + u]'),
			new rButton('strikethrough',			rTypeRich,						rActionBasic,'Зачеркнутый'),
		new rButton('spacer',rTypeNone),
			new rButton('subscript',					rTypeRich,						rActionBasic,'Подстрочный'),
			new rButton('superscript',				rTypeRich,						rActionBasic,'Надстрочный'),
		new rButton('spacer',rTypeNone),
			new rButton('justifynone',				rTypeRich,						rActionBasic,'По левому краю'),
			new rButton('justifycenter',			rTypeRich,						rActionBasic,'По центру'),
			new rButton('justifyright',				rTypeRich,						rActionBasic,'По правому краю'),
			new rButton('justifyfull',				rTypeRich,						rActionBasic,'По ширине'),
		new rButton('spacer',rTypeNone),
			new rButton('insertorderedlist',	rTypeRich,						rActionBasic,'Нумерация'),
			new rButton('insertunorderedlist',rTypeRich,						rActionBasic,'Маркеры'),
		new rButton('spacer',rTypeNone),
			new rButton('outdent',						rTypeRich,						rActionBasic,'Уменьшить отступ'),
			new rButton('indent',							rTypeRich,						rActionBasic,'Увеличить отступ'),
		new rButton('spacer',rTypeNone),
			new rButton('showspecial',				rTypeRich,						rActionExtend,'Разметка документа'),
			new rButton('html',								rTypeRich|rTypeText,	rActionExtend,'Режим редактирования'),
		new rButton('break',rTypeNone),
			new	rSelect('formatblock',				rTypeRich,						rActionExtend|rActionText,Array("","<p>","Normal","<h1>","<h2>","<h3>","<h4>","<h5>","<h6>"),Array("","Параграф","Нормальный","Заголовок 1","Заголовок 2","Заголовок 3","Заголовок 4","Заголовок 5","Заголовок 6")),
		new rButton('spacer',rTypeNone),
			new rButton('breakall',						rTypeRich,						rActionExtend,'Новая строка'),
			new rButton('hr',									rTypeRich,						rActionExtend,'Горизонтальная линия')
		);
		// свойство : Разметка документа
		this.showspecial = false;
		// метод : инициализация панели инструментов RE
		this.initialize = rPanel_initialize;
		// метод : нажатие кнопки на панели
		this.action = rPanel_action;
		// метод : обновить состояние кнопок на панеле
		this.update = rPanel_update;
		// создаем едиственную копию себя самого и инициализируем ее
		if(orPanel==null){
			orPanel = this;
			orPanel.initialize();
		}
	}
// -------------------------------------------------------------------------------
// --- методы класса rPanel
// -------------------------------------------------------------------------------
	function rPanel_initialize(){ // инициализация панели инструментов RE
		if(orPanel==this){ // только одна панель может существовать в системе
			var html = "<div id='rPanel'>"; // вывод HTML кнопок с командами 
			for(var i=0; i<this.commands.length; i++){
				if(this.commands[i].name=='break'){
					html += '<br>';
				}else if(this.commands[i].name=='spacer'){
					html += '<img src="'+orPath.base+orPath.image+"re_"+this.commands[i].name+'.gif" width=5 height=16 border=0>';
				}else if(this.commands[i].name=='libraryimages' && orImages==null){
				}else if(this.commands[i].name=='libraryfiles' && orLinks==null){
				}else if(this.commands[i].classType=='select'){
					html += '<select id="rPanel_'+this.commands[i].name+'" ';
					html += ' onChange="orPanel.action('+i+');">';
					for(var j=0; j<this.commands[i].values.length; j++){
						html += '<option value="'+this.commands[i].values[j]+'">'+this.commands[i].titles[j];
					}
					html += '</select>';
				}else{
					html += '<button id="rPanel_'+this.commands[i].name+'" ';
					html += ' onClick="orPanel.action('+i+');" ';
					html += ' onMouseOver="if(!this.disabled){ this.classNameReal = this.className; this.className = \'hover\';}"';
					html += ' onMouseOut="if(!this.disabled){ this.className = this.classNameReal;}"';
					html += '	title="'+this.commands[i].title+'">';
					html += '<img src="'+orPath.base+orPath.image+"re_"+this.commands[i].name+'.gif" width=16 height=16 border=0>';
					html += '</button>';
				}
			}
			html += "</div>";
			document.write(html);
			for(var i=0; i<this.commands.length; i++){ // собираем созданные объекты
				if(document.all['rPanel_'+this.commands[i].name]){
					this.commands[i].button = document.all['rPanel_'+this.commands[i].name];	
				}
			}
			this.update();
		}
	}
// --- 
	function rPanel_action(command){ // нажатие кнопки на панеле инструментов RE
		if(orTextActive!=null){
			var sRange = null;
			var mode = orTextActive.type; // состояние активного поля редактирования
			orTextActive.editor.focus();
			if((this.commands[command].type & mode) != 0){
				if(mode == rTypeRich){	// если режим позволяет, то достаем, что выделено
					orTextActive.edocument.document.body.focus();
					sRange = orTextActive.edocument.document.selection.createRange();
				}
				if(this.commands[command].action==rActionBasic){
					switch(this.commands[command].name){
					// --- нижний индекс
						case 'subscript':
							if(sRange.queryCommandState('superscript')) sRange.execCommand('superscript');
							sRange.execCommand('subscript');
						break;
					// --- верхний индекс
						case 'superscript': 
							if(sRange.queryCommandState('subscript')) sRange.execCommand('subscript');
							sRange.execCommand('superscript');
						break;
					// --- стандартные команды
						default:
							if(sRange.queryCommandEnabled(this.commands[command].name)) 
							sRange.execCommand(this.commands[command].name);
						break;
					}
				}else if((this.commands[command].action & rActionExtend) == rActionExtend){
					switch(this.commands[command].name){
					// --- разметка документа
						case 'showspecial':
							this.showspecial = !this.showspecial;
						break;
					// --- переключение режимов
						case 'html':
							orTextActive.tswitch((mode==rTypeText)?rTypeRich:rTypeText);
							this.update();
						break;
					// --- другие команды
						default:
							if((this.commands[command].action & rActionText) == rActionText){
								if(sRange==null || sRange.length==1) break;							
							}else	if((this.commands[command].action & rActionObject) == rActionObject){
								if(sRange==null || sRange.length!=1) break;							
							}
							eval("rAction_"+this.commands[command].name+"(sRange);");
						break;
					}
				}
				orTextActive.synchro();	
			}	
		}
	}
// --- 
	function rPanel_update(){ // обновить состояние кнопок на панеле инструментов RE
		var mode = (orTextActive!=null)?orTextActive.type:rTypeNone; // состояние активного поля редактирования
		// Обновляем состояния кнопок с командами
		for(var i=0; i<this.commands.length; i++){
			if(this.commands[i].button!=null){
				if((this.commands[i].type & mode) == 0){
					this.commands[i].button.disabled = true;
					this.commands[i].button.classNameReal = 'lock';
				}else{
					this.commands[i].button.disabled = false;
					if(this.commands[i].name=="html") // --- переключение режимов
						this.commands[i].button.classNameReal = (mode==rTypeText)?"down":"";
					else if(this.commands[i].name=="showspecial"){ // --- разметка документа
						this.commands[i].button.classNameReal = (this.showspecial)?"down":"";
						orTextActive.edocument.document.body.className = (this.showspecial)?"richedit showspecial":"richedit";
					}else
						this.commands[i].button.classNameReal = "";
				}
				this.commands[i].button.className = this.commands[i].button.classNameReal;
			}
		}
	}
// -------------------------------------------------------------------------------
// --- Функции обработчики нажатия кнопок панели
// -------------------------------------------------------------------------------
// --- очистка стилей
	function rAction_clearformat(sRange){
		if(confirm("Внимание!\nВыполнение данной операции приведет к удалению всех стилей выделенного фрагмента.\nНекоторое форматирование текста может быть потерянно.\nПродолжить?")){
			var orDocument = orTextActive.edocument.document;
			rClearObjectFormat(sRange.parentElement(),orDocument);
		}
	}
// --- цвет ячейки
	function rAction_bgcolor(sRange){	
		var elmTD = rGetParent(sRange.parentElement(),"TD");
		if(elmTD!=null){	// выделена одна ячейка
			var color = elmTD.bgColor;
			elmTD.bgColor =	rGetColorer(color);
		}
	}
// --- breakall
	function rAction_breakall(sRange){
		sRange.collapse(false);
		sRange.pasteHTML("<br clear=all>");
	}
// --- hr
	function rAction_hr(sRange){
		sRange.collapse(false);
		sRange.pasteHTML("<hr>");
	}
// --- цвет текста
	function rAction_formatblock(sRange){	
		var value = document.getElementById("rPanel_formatblock").value;
		if(value=="Normal"){
			sRange.execCommand('formatblock',false, "<p>");		
			var oObject = rGetParent(sRange.parentElement(),"P");
			oObject.outerHTML = oObject.innerHTML;
		}else{
			sRange.execCommand('formatblock',false, value);
		}
		document.getElementById("rPanel_formatblock").selectedIndex = 0;
	}

// --- цвет текста
	function rAction_forecolor(sRange){	
		if(!sRange.queryCommandEnabled("forecolor")) return;
		var color = sRange.queryCommandValue("forecolor");
		color = (color)?toHex(colorToRGB(color)):"";
		color =	rGetColorer(color);
		sRange.execCommand("forecolor",false,color);
	}
// --- вставка ссылки
	function rAction_createlink(sRange){
		window.showModalDialog(orPath.base+"richedit.createlink.html",sRange,"dialogWidth:203px; dialogHeight:220px; resizable: no; help: no; status: no; scroll: no;");
	}
// --- свойства изображения
	function rAction_imageproperties(sRange){
		if(sRange.item(0).tagName.toUpperCase() != "IMG")	return;
		window.showModalDialog(orPath.base+"richedit.imageproperties.html",sRange,"dialogWidth:203px; dialogHeight:320px; resizable: no; help: no; status: no; scroll: no;");
	}
// --- свойства таблицы
	function rAction_tableproperties(sRange){
		if(sRange.item(0).tagName.toUpperCase() != "TABLE")	return;
		window.showModalDialog(orPath.base+"richedit.tableproperties.html",sRange,"dialogWidth:203px; dialogHeight:350px; resizable: no; help: no; status: no; scroll: no;");
	}
// --- вставка таблицы
	function rAction_inserttable(sRange){
		window.showModalDialog(orPath.base+"richedit.inserttable.html",sRange,"dialogWidth:298px; dialogHeight:325px; resizable:no; help:no; status:no; scroll:no;title:no;");
	}
// --- библиотека файлов
	function rAction_libraryfiles(sRange){	
		wrLinks = window.open(orPath.base+'richedit.libraryfiles.phtml', "richfiles", "width=193px,height=335,status=no,scrollbars=no,resizable=no");
		wrLinks.focus();
	}
// --- библиотека изображений
	function rAction_libraryimages(sRange){
		wrImages = window.open(orPath.base+'richedit.libraryimages.phtml?h='+orImages.height+'&w='+orImages.width, "richimages", "status=no,scrollbars=no,resizable=no,width=780,height=420");
		wrImages.focus();
	}
// --- удаление строки
	function rAction_deleterow(sRange){
		var elmTR = rGetParent(sRange.parentElement(),"TR");
		if(elmTR!=null){	// выделена одна строка
			var elmTABLE = rGetParent(elmTR,"TABLE");		// ищем родительский TABLE
			if(elmTABLE.rows.length==1){							
			// --- удаляем таблицу целиком
				elmTABLE.removeNode(true);
			}else{
			// --- исправляем rowSpan строки снизу удаляемой строки
				if(elmTABLE.rows[elmTR.rowIndex+1]){
					var mTABLE = new rMatrix(elmTABLE);  
					var mPos = mTABLE.position(elmTR.cells[0]); 
					var rowPos = mPos.row;
					var newTR	 = elmTABLE.rows[elmTR.rowIndex+1].cloneNode(false);
					var cellIndex = -1;
					for(var i=0; i<mTABLE.mcols; i++){
						if(cellIndex !=	mTABLE.matrix[rowPos+1][i]){
							cellIndex =	mTABLE.matrix[rowPos+1][i];
							if(rowPos==0 || mTABLE.matrix[rowPos-1][i]!=cellIndex){
								var newTD = elmTABLE.cells[cellIndex].cloneNode(true);
								if(mTABLE.matrix[rowPos][i]==cellIndex) newTD.setAttribute("rowSpan",elmTABLE.cells[cellIndex].rowSpan-1);
								newTR.appendChild(newTD);
							}					
						}
					}
				elmTABLE.rows[elmTR.rowIndex+1].parentNode.replaceChild(newTR,elmTABLE.rows[elmTR.rowIndex+1]);
				}
			// --- исправляем rowSpan строк ссверху удаляемой строки
				for(var i=0; i<elmTR.rowIndex; i++){
					var tempTR = elmTABLE.rows(i);
					for(var j=0; j<tempTR.cells.length; j++){
						if(tempTR.cells(j).rowSpan>(elmTR.rowIndex - i)) tempTR.cells(j).rowSpan--;
					}
				}
			// --- удаляем строку 
				elmTABLE.deleteRow(elmTR.rowIndex);
			}
		}
	}
// --- вставка строки
	function rAction_insertrow(sRange){
		var elmTR = rGetParent(sRange.parentElement(),"TR");
		if(elmTR!=null){	// выделена одна строка
			var elmTABLE = rGetParent(elmTR,"TABLE");		// ищем родительский TABLE
      var newTR = elmTABLE.insertRow(elmTR.rowIndex+1);
			// --- вставляем строку по образу и подобию
      for(var i=0; i<elmTR.cells.length; i++){
        if (elmTR.cells(i).rowSpan>1) 
					elmTR.cells(i).rowSpan++;
        else{
          var newTD = elmTR.cells(i).cloneNode();
          newTR.appendChild(newTD);
        }
      }
			// --- исправляем rowSpan строк ссверху вставленой строки
      for(var i=0; i<elmTR.rowIndex; i++){
        var tempTR = elmTABLE.rows(i);
        for(var j=0; j<tempTR.cells.length; j++){
          if(tempTR.cells(j).rowSpan>(elmTR.rowIndex - i)) tempTR.cells(j).rowSpan++;
        }
      }
		}
	}
// --- объединить ячейку с правой
	function rAction_mergeright(sRange){ 
		var elmTD = rGetParent(sRange.parentElement(),"TD");
		if(elmTD!=null){
			var elmTABLE = rGetParent(elmTD,"TABLE");
			var mTABLE = new rMatrix(elmTABLE);  
			var mPos = mTABLE.position(elmTD); 
			var nPos = mTABLE.nearest(mPos,'right');
			if(nPos){ 
				var nextTD	= elmTABLE.cells[mTABLE.index(nPos)];
				if(nPos.row==mPos.row && nextTD.rowSpan==elmTD.rowSpan){
					elmTD.innerHTML = elmTD.innerHTML+" "+nextTD.innerHTML;
					elmTD.colSpan = elmTD.colSpan+nextTD.colSpan;
					nextTD.parentNode.deleteCell(nextTD.cellIndex);
				}
			}
		}
	}
// --- объединить ячейку с нижней
	function rAction_mergedown(sRange){ 
		var elmTD = rGetParent(sRange.parentElement(),"TD");
		if(elmTD!=null){
			var elmTABLE = rGetParent(elmTD,"TABLE");
			var mTABLE = new rMatrix(elmTABLE);  
			var mPos = mTABLE.position(elmTD); 
			var nPos = mTABLE.nearest(mPos,'bottom');
			if(nPos){ 
				var nextTD	= elmTABLE.cells[mTABLE.index(nPos)];
				if(nPos.col==mPos.col && nextTD.colSpan==elmTD.colSpan){
					elmTD.innerHTML = elmTD.innerHTML+"<br>"+nextTD.innerHTML;
					elmTD.rowSpan = elmTD.rowSpan+nextTD.rowSpan;
					nextTD.parentNode.deleteCell(nextTD.cellIndex);
				}
			}
		}
	}
// --- снять объединение с ячеек
	function rAction_mergenone(sRange){ 
		var elmTD = rGetParent(sRange.parentElement(),"TD");
		if(elmTD!=null&&elmTD.colSpan*elmTD.rowSpan){
			var elmTABLE = rGetParent(elmTD,"TABLE");
			var mTABLE = new rMatrix(elmTABLE);  
			var mPos = mTABLE.position(elmTD);
			var colSpan = elmTD.colSpan; elmTD.colSpan = 1;
			var rowSpan = elmTD.rowSpan; elmTD.rowSpan = 1;
			for(var i=0;i<rowSpan;i++){
				if(i>0){
					var isReal = false;
					var colNum = -1;
					for(var j=0;j<mTABLE.mcols;j++){
						if(mTABLE.matrix[mPos.row+i][j]!=mTABLE.matrix[mPos.row+i-1][j]){
							isReal = true;
							if(j>colNum && j<mPos.col) colNum = j;
						}
					}
					if(colNum>=0 && colNum<mPos.col){
						var nTD = elmTABLE.cells[mTABLE.matrix[mPos.row+i][colNum]+i*colSpan-1];
						nTD.parentNode.replaceChild(elmTD.cloneNode(false),nTD.parentNode.insertCell(nTD.cellIndex+1));
						elmTD = nTD.parentNode.cells[nTD.cellIndex+1];
					}else{
						var nTR = (isReal)?elmTABLE.rows[elmTD.parentNode.rowIndex+1]:elmTABLE.insertRow(elmTD.parentNode.rowIndex+1);
						nTR.replaceChild(elmTD.cloneNode(false),nTR.insertCell(0));
						elmTD = nTR.cells[0];
					}
					mTABLE.matrix[mPos.row+i][mPos.col+j-1]
				}
				for(var j=1;j<colSpan;j++)
					elmTD.parentNode.replaceChild(elmTD.cloneNode(false),elmTD.parentNode.insertCell(elmTD.cellIndex+j));
			}
		}
	}
// --- вставка столбца
	function rAction_insertcol(sRange){
		var elmTD = rGetParent(sRange.parentElement(),"TD");
		if(elmTD!=null){
			var elmTABLE = rGetParent(elmTD,"TABLE");
			var mTABLE = new rMatrix(elmTABLE);  
			var mPos = mTABLE.position(elmTD); 
			if(mPos){ 
				var oTD = null;
				for(var i=mTABLE.mrows-1;i>=0;i--){
					var j = mPos.col;
					if(j==0){
						elmTABLE.rows[i].insertCell(0);
					}else	if(mTABLE.matrix[i][j] == mTABLE.matrix[i][j-1]){
						oTD = elmTABLE.cells[mTABLE.matrix[i][j]];
						oTD.colSpan ++;
						i -= (oTD.rowSpan-1);
					}else if(i==0){
						oTD = elmTABLE.cells[mTABLE.matrix[i][j-1]];
						oTD.parentNode.insertCell(oTD.cellIndex+1);
					}else{
						do{
							j--;
						}while(j>0 && mTABLE.matrix[i][j] == mTABLE.matrix[i-1][j]);
						if(j==0 && mTABLE.matrix[i][0] == mTABLE.matrix[i-1][0]){
							elmTABLE.rows[i].insertCell(0);
						}else{
							oTD = elmTABLE.cells[mTABLE.matrix[i][j]];
							oTD.parentNode.insertCell(oTD.cellIndex+1);
						}
					}
				}
			}
		}
	}
// --- удаление столбца
	function rAction_deletecol(sRange){
		var elmTD = rGetParent(sRange.parentElement(),"TD");
		if(elmTD!=null){
			var elmTABLE = rGetParent(elmTD,"TABLE");
			var mTABLE = new rMatrix(elmTABLE);  
			var mPos = mTABLE.position(elmTD); 
			if(mPos){ 
				var oTD = null;
				for(var i=mTABLE.mrows-1;i>=0;i--){
					mPos.row = i;
					oTD = elmTABLE.cells[mTABLE.index(mPos)];
					i -= (oTD.rowSpan-1);
					if(oTD.colSpan>1){
						oTD.colSpan --;
					}else{
						oTD.parentNode.deleteCell(oTD.cellIndex);
					}
				}
			}
		}
	}


