--- /dev/null
+/*\r
+ * FCKeditor - The text editor for Internet - http://www.fckeditor.net\r
+ * Copyright (C) 2003-2009 Frederico Caldeira Knabben\r
+ *\r
+ * == BEGIN LICENSE ==\r
+ *\r
+ * Licensed under the terms of any of the following licenses at your\r
+ * choice:\r
+ *\r
+ * - GNU General Public License Version 2 or later (the "GPL")\r
+ * http://www.gnu.org/licenses/gpl.html\r
+ *\r
+ * - GNU Lesser General Public License Version 2.1 or later (the "LGPL")\r
+ * http://www.gnu.org/licenses/lgpl.html\r
+ *\r
+ * - Mozilla Public License Version 1.1 or later (the "MPL")\r
+ * http://www.mozilla.org/MPL/MPL-1.1.html\r
+ *\r
+ * == END LICENSE ==\r
+ *\r
+ * FCKJustifyCommand Class: controls block justification.\r
+ */\r
+\r
+var FCKJustifyCommand = function( alignValue )\r
+{\r
+ this.AlignValue = alignValue ;\r
+\r
+ // Detect whether this is the instance for the default alignment.\r
+ var contentDir = FCKConfig.ContentLangDirection.toLowerCase() ;\r
+ this.IsDefaultAlign = ( alignValue == 'left' && contentDir == 'ltr' ) ||\r
+ ( alignValue == 'right' && contentDir == 'rtl' ) ;\r
+\r
+ // Get the class name to be used by this instance.\r
+ var cssClassName = this._CssClassName = ( function()\r
+ {\r
+ var classes = FCKConfig.JustifyClasses ;\r
+ if ( classes )\r
+ {\r
+ switch ( alignValue )\r
+ {\r
+ case 'left' :\r
+ return classes[0] || null ;\r
+ case 'center' :\r
+ return classes[1] || null ;\r
+ case 'right' :\r
+ return classes[2] || null ;\r
+ case 'justify' :\r
+ return classes[3] || null ;\r
+ }\r
+ }\r
+ return null ;\r
+ } )() ;\r
+\r
+ if ( cssClassName && cssClassName.length > 0 )\r
+ this._CssClassRegex = new RegExp( '(?:^|\\s+)' + cssClassName + '(?=$|\\s)' ) ;\r
+}\r
+\r
+FCKJustifyCommand._GetClassNameRegex = function()\r
+{\r
+ var regex = FCKJustifyCommand._ClassRegex ;\r
+ if ( regex != undefined )\r
+ return regex ;\r
+\r
+ var names = [] ;\r
+\r
+ var classes = FCKConfig.JustifyClasses ;\r
+ if ( classes )\r
+ {\r
+ for ( var i = 0 ; i < 4 ; i++ )\r
+ {\r
+ var className = classes[i] ;\r
+ if ( className && className.length > 0 )\r
+ names.push( className ) ;\r
+ }\r
+ }\r
+\r
+ if ( names.length > 0 )\r
+ regex = new RegExp( '(?:^|\\s+)(?:' + names.join( '|' ) + ')(?=$|\\s)' ) ;\r
+ else\r
+ regex = null ;\r
+\r
+ return FCKJustifyCommand._ClassRegex = regex ;\r
+}\r
+\r
+FCKJustifyCommand.prototype =\r
+{\r
+ Execute : function()\r
+ {\r
+ // Save an undo snapshot before doing anything.\r
+ FCKUndo.SaveUndoStep() ;\r
+\r
+ var range = new FCKDomRange( FCK.EditorWindow ) ;\r
+ range.MoveToSelection() ;\r
+\r
+ var currentState = this.GetState() ;\r
+ if ( currentState == FCK_TRISTATE_DISABLED )\r
+ return ;\r
+\r
+ // Store a bookmark of the selection since the paragraph iterator might\r
+ // change the DOM tree and break selections.\r
+ var bookmark = range.CreateBookmark() ;\r
+\r
+ var cssClassName = this._CssClassName ;\r
+\r
+ // Apply alignment setting for each paragraph.\r
+ var iterator = new FCKDomRangeIterator( range ) ;\r
+ var block ;\r
+ while ( ( block = iterator.GetNextParagraph() ) )\r
+ {\r
+ block.removeAttribute( 'align' ) ;\r
+\r
+ if ( cssClassName )\r
+ {\r
+ // Remove the any of the alignment classes from the className.\r
+ var className = block.className.replace( FCKJustifyCommand._GetClassNameRegex(), '' ) ;\r
+\r
+ // Append the desired class name.\r
+ if ( currentState == FCK_TRISTATE_OFF )\r
+ {\r
+ if ( className.length > 0 )\r
+ className += ' ' ;\r
+ block.className = className + cssClassName ;\r
+ }\r
+ else if ( className.length == 0 )\r
+ FCKDomTools.RemoveAttribute( block, 'class' ) ;\r
+ }\r
+ else\r
+ {\r
+ var style = block.style ;\r
+ if ( currentState == FCK_TRISTATE_OFF )\r
+ style.textAlign = this.AlignValue ;\r
+ else\r
+ {\r
+ style.textAlign = '' ;\r
+ if ( style.cssText.length == 0 )\r
+ block.removeAttribute( 'style' ) ;\r
+ }\r
+ }\r
+ }\r
+\r
+ // Restore previous selection.\r
+ range.MoveToBookmark( bookmark ) ;\r
+ range.Select() ;\r
+\r
+ FCK.Focus() ;\r
+ FCK.Events.FireEvent( 'OnSelectionChange' ) ;\r
+ },\r
+\r
+ GetState : function()\r
+ {\r
+ // Disabled if not WYSIWYG.\r
+ if ( FCK.EditMode != FCK_EDITMODE_WYSIWYG || ! FCK.EditorWindow )\r
+ return FCK_TRISTATE_DISABLED ;\r
+\r
+ // Retrieve the first selected block.\r
+ var path = new FCKElementPath( FCKSelection.GetBoundaryParentElement( true ) ) ;\r
+ var firstBlock = path.Block || path.BlockLimit ;\r
+\r
+ if ( !firstBlock || firstBlock.nodeName.toLowerCase() == 'body' )\r
+ return FCK_TRISTATE_OFF ;\r
+\r
+ // Check if the desired style is already applied to the block.\r
+ var currentAlign ;\r
+ if ( FCKBrowserInfo.IsIE )\r
+ currentAlign = firstBlock.currentStyle.textAlign ;\r
+ else\r
+ currentAlign = FCK.EditorWindow.getComputedStyle( firstBlock, '' ).getPropertyValue( 'text-align' );\r
+ currentAlign = currentAlign.replace( /(-moz-|-webkit-|start|auto)/i, '' );\r
+ if ( ( !currentAlign && this.IsDefaultAlign ) || currentAlign == this.AlignValue )\r
+ return FCK_TRISTATE_ON ;\r
+ return FCK_TRISTATE_OFF ;\r
+ }\r
+} ;\r