| | 1 | /* |
| | 2 | Copyright (c) 2003-2009, CKSource - Frederico Knabben. All rights reserved. |
| | 3 | For licensing, see LICENSE.html or http://ckeditor.com/license |
| | 4 | */ |
| | 5 | |
| | 6 | /** |
| | 7 | * @file Justify commands. |
| | 8 | */ |
| | 9 | |
| | 10 | (function() |
| | 11 | { |
| | 12 | var alignRemoveRegex = /(-moz-|-webkit-|start|auto)/i; |
| | 13 | |
| | 14 | function getState( editor, path ) |
| | 15 | { |
| | 16 | var firstBlock = path.block || path.blockLimit; |
| | 17 | |
| | 18 | if ( !firstBlock || firstBlock.getName() == 'body' ) |
| | 19 | return CKEDITOR.TRISTATE_OFF; |
| | 20 | |
| | 21 | var currentAlign = firstBlock.getComputedStyle( 'text-align' ).replace( alignRemoveRegex, '' ); |
| | 22 | if ( ( !currentAlign && this.isDefaultAlign ) || currentAlign == this.value ) |
| | 23 | return CKEDITOR.TRISTATE_ON; |
| | 24 | return CKEDITOR.TRISTATE_OFF; |
| | 25 | } |
| | 26 | |
| | 27 | function onSelectionChange( evt ) |
| | 28 | { |
| | 29 | var command = evt.editor.getCommand( this.name ); |
| | 30 | command.state = getState.call( this, evt.editor, evt.data.path ); |
| | 31 | command.fire( 'state' ); |
| | 32 | } |
| | 33 | |
| | 34 | function justifyCommand( editor, name, value ) |
| | 35 | { |
| | 36 | this.name = name; |
| | 37 | this.value = value; |
| | 38 | |
| | 39 | var contentDir = editor.config.contentsLangDirection; |
| | 40 | this.isDefaultAlign = ( value == 'left' && contentDir == 'ltr' ) || |
| | 41 | ( value == 'right' && contentDir == 'rtl' ); |
| | 42 | |
| | 43 | var classes = editor.config.justifyClasses; |
| | 44 | if ( classes ) |
| | 45 | { |
| | 46 | switch ( value ) |
| | 47 | { |
| | 48 | case 'left' : |
| | 49 | this.cssClassName = classes[0]; |
| | 50 | break; |
| | 51 | case 'center' : |
| | 52 | this.cssClassName = classes[1]; |
| | 53 | break; |
| | 54 | case 'right' : |
| | 55 | this.cssClassName = classes[2]; |
| | 56 | break; |
| | 57 | case 'justify' : |
| | 58 | this.cssClassName = classes[3]; |
| | 59 | break; |
| | 60 | } |
| | 61 | |
| | 62 | this.cssClassRegex = new RegExp( '(?:^|\\s+)(?:' + classes.join( '|' ) + ')(?=$|\\s)' ); |
| | 63 | } |
| | 64 | } |
| | 65 | |
| | 66 | justifyCommand.prototype = { |
| | 67 | exec : function( editor ) |
| | 68 | { |
| | 69 | var selection = editor.getSelection(), |
| | 70 | range = selection && selection.getRanges()[0]; |
| | 71 | |
| | 72 | if ( !range ) |
| | 73 | return; |
| | 74 | |
| | 75 | var bookmarks = selection.createBookmarks(), |
| | 76 | cssClassName = this.cssClassName, |
| | 77 | iterator = range.createIterator(), |
| | 78 | block; |
| | 79 | |
| | 80 | while ( ( block = iterator.getNextParagraph() ) ) |
| | 81 | { |
| | 82 | block.removeAttribute( 'align' ); |
| | 83 | |
| | 84 | if ( cssClassName ) |
| | 85 | { |
| | 86 | // Remove any of the alignment classes from the className. |
| | 87 | var className = block.$.className = |
| | 88 | CKEDITOR.tools.ltrim( block.$.className.replace( this.cssClassRegex, '' ) ); |
| | 89 | |
| | 90 | // Append the desired class name. |
| | 91 | if ( this.state == CKEDITOR.TRISTATE_OFF && !this.isDefaultAlign ) |
| | 92 | block.addClass( cssClassName ); |
| | 93 | else if ( className.length == 0 ) |
| | 94 | block.removeAttribute( 'class' ); |
| | 95 | } |
| | 96 | else |
| | 97 | { |
| | 98 | if ( this.state == CKEDITOR.TRISTATE_OFF && !this.isDefaultAlign ) |
| | 99 | block.setStyle( 'text-align', this.value ); |
| | 100 | else |
| | 101 | block.removeStyle( 'text-align' ); |
| | 102 | } |
| | 103 | } |
| | 104 | |
| | 105 | editor.focus(); |
| | 106 | editor.forceNextSelectionCheck(); |
| | 107 | selection.selectBookmarks( bookmarks ); |
| | 108 | } |
| | 109 | }; |
| | 110 | |
| | 111 | CKEDITOR.plugins.add( 'justify', |
| | 112 | { |
| | 113 | init : function( editor ) |
| | 114 | { |
| | 115 | var left = new justifyCommand( editor, 'justifyleft', 'left' ), |
| | 116 | center = new justifyCommand( editor, 'justifycenter', 'center' ), |
| | 117 | right = new justifyCommand( editor, 'justifyright', 'right' ), |
| | 118 | justify = new justifyCommand( editor, 'justifyblock', 'justify' ); |
| | 119 | |
| | 120 | editor.addCommand( 'justifyleft', left ); |
| | 121 | editor.addCommand( 'justifycenter', center ); |
| | 122 | editor.addCommand( 'justifyright', right ); |
| | 123 | editor.addCommand( 'justifyblock', justify ); |
| | 124 | |
| | 125 | editor.ui.addButton( 'JustifyLeft', |
| | 126 | { |
| | 127 | label : editor.lang.justify.left, |
| | 128 | command : 'justifyleft' |
| | 129 | } ); |
| | 130 | editor.ui.addButton( 'JustifyCenter', |
| | 131 | { |
| | 132 | label : editor.lang.justify.center, |
| | 133 | command : 'justifycenter' |
| | 134 | } ); |
| | 135 | editor.ui.addButton( 'JustifyRight', |
| | 136 | { |
| | 137 | label : editor.lang.justify.right, |
| | 138 | command : 'justifyright' |
| | 139 | } ); |
| | 140 | editor.ui.addButton( 'JustifyBlock', |
| | 141 | { |
| | 142 | label : editor.lang.justify.block, |
| | 143 | command : 'justifyblock' |
| | 144 | } ); |
| | 145 | |
| | 146 | editor.on( 'selectionChange', CKEDITOR.tools.bind( onSelectionChange, left ) ); |
| | 147 | editor.on( 'selectionChange', CKEDITOR.tools.bind( onSelectionChange, right ) ); |
| | 148 | editor.on( 'selectionChange', CKEDITOR.tools.bind( onSelectionChange, center ) ); |
| | 149 | editor.on( 'selectionChange', CKEDITOR.tools.bind( onSelectionChange, justify ) ); |
| | 150 | }, |
| | 151 | |
| | 152 | requires : [ 'domiterator' ] |
| | 153 | }); |
| | 154 | })(); |
| | 155 | |
| | 156 | CKEDITOR.tools.extend( CKEDITOR.config, |
| | 157 | { |
| | 158 | justifyClasses : null |
| | 159 | } ); |