[239] | 1 | /*
|
---|
| 2 | * Copyright (c) 2003-2011, CKSource - Frederico Knabben. All rights reserved.
|
---|
| 3 | * For licensing, see LICENSE.html or http://ckeditor.com/license
|
---|
| 4 | */
|
---|
| 5 |
|
---|
| 6 | (function()
|
---|
| 7 | {
|
---|
| 8 |
|
---|
| 9 | /**
|
---|
| 10 | * Add to collection with DUP examination.
|
---|
| 11 | * @param {Object} collection
|
---|
| 12 | * @param {Object} element
|
---|
| 13 | * @param {Object} database
|
---|
| 14 | */
|
---|
| 15 | function addSafely( collection, element, database )
|
---|
| 16 | {
|
---|
| 17 | // 1. IE doesn't support customData on text nodes;
|
---|
| 18 | // 2. Text nodes never get chance to appear twice;
|
---|
| 19 | if ( !element.is || !element.getCustomData( 'block_processed' ) )
|
---|
| 20 | {
|
---|
| 21 | element.is && CKEDITOR.dom.element.setMarker( database, element, 'block_processed', true );
|
---|
| 22 | collection.push( element );
|
---|
| 23 | }
|
---|
| 24 | }
|
---|
| 25 |
|
---|
| 26 | function getNonEmptyChildren( element )
|
---|
| 27 | {
|
---|
| 28 | var retval = [];
|
---|
| 29 | var children = element.getChildren();
|
---|
| 30 | for ( var i = 0 ; i < children.count() ; i++ )
|
---|
| 31 | {
|
---|
| 32 | var child = children.getItem( i );
|
---|
| 33 | if ( ! ( child.type === CKEDITOR.NODE_TEXT
|
---|
| 34 | && ( /^[ \t\n\r]+$/ ).test( child.getText() ) ) )
|
---|
| 35 | retval.push( child );
|
---|
| 36 | }
|
---|
| 37 | return retval;
|
---|
| 38 | }
|
---|
| 39 |
|
---|
| 40 |
|
---|
| 41 | /**
|
---|
| 42 | * Dialog reused by both 'creatediv' and 'editdiv' commands.
|
---|
| 43 | * @param {Object} editor
|
---|
| 44 | * @param {String} command The command name which indicate what the current command is.
|
---|
| 45 | */
|
---|
| 46 | function divDialog( editor, command )
|
---|
| 47 | {
|
---|
| 48 | // Definition of elements at which div operation should stopped.
|
---|
| 49 | var divLimitDefinition = ( function(){
|
---|
| 50 |
|
---|
| 51 | // Customzie from specialize blockLimit elements
|
---|
| 52 | var definition = CKEDITOR.tools.extend( {}, CKEDITOR.dtd.$blockLimit );
|
---|
| 53 |
|
---|
| 54 | // Exclude 'div' itself.
|
---|
| 55 | delete definition.div;
|
---|
| 56 |
|
---|
| 57 | // Exclude 'td' and 'th' when 'wrapping table'
|
---|
| 58 | if ( editor.config.div_wrapTable )
|
---|
| 59 | {
|
---|
| 60 | delete definition.td;
|
---|
| 61 | delete definition.th;
|
---|
| 62 | }
|
---|
| 63 | return definition;
|
---|
| 64 | })();
|
---|
| 65 |
|
---|
| 66 | // DTD of 'div' element
|
---|
| 67 | var dtd = CKEDITOR.dtd.div;
|
---|
| 68 |
|
---|
| 69 | /**
|
---|
| 70 | * Get the first div limit element on the element's path.
|
---|
| 71 | * @param {Object} element
|
---|
| 72 | */
|
---|
| 73 | function getDivLimitElement( element )
|
---|
| 74 | {
|
---|
| 75 | var pathElements = new CKEDITOR.dom.elementPath( element ).elements;
|
---|
| 76 | var divLimit;
|
---|
| 77 | for ( var i = 0; i < pathElements.length ; i++ )
|
---|
| 78 | {
|
---|
| 79 | if ( pathElements[ i ].getName() in divLimitDefinition )
|
---|
| 80 | {
|
---|
| 81 | divLimit = pathElements[ i ];
|
---|
| 82 | break;
|
---|
| 83 | }
|
---|
| 84 | }
|
---|
| 85 | return divLimit;
|
---|
| 86 | }
|
---|
| 87 |
|
---|
| 88 | /**
|
---|
| 89 | * Init all fields' setup/commit function.
|
---|
| 90 | * @memberof divDialog
|
---|
| 91 | */
|
---|
| 92 | function setupFields()
|
---|
| 93 | {
|
---|
| 94 | this.foreach( function( field )
|
---|
| 95 | {
|
---|
| 96 | // Exclude layout container elements
|
---|
| 97 | if ( /^(?!vbox|hbox)/.test( field.type ) )
|
---|
| 98 | {
|
---|
| 99 | if ( !field.setup )
|
---|
| 100 | {
|
---|
| 101 | // Read the dialog fields values from the specified
|
---|
| 102 | // element attributes.
|
---|
| 103 | field.setup = function( element )
|
---|
| 104 | {
|
---|
| 105 | field.setValue( element.getAttribute( field.id ) || '' );
|
---|
| 106 | };
|
---|
| 107 | }
|
---|
| 108 | if ( !field.commit )
|
---|
| 109 | {
|
---|
| 110 | // Set element attributes assigned by the dialog
|
---|
| 111 | // fields.
|
---|
| 112 | field.commit = function( element )
|
---|
| 113 | {
|
---|
| 114 | var fieldValue = this.getValue();
|
---|
| 115 | // ignore default element attribute values
|
---|
| 116 | if ( 'dir' == field.id && element.getComputedStyle( 'direction' ) == fieldValue )
|
---|
| 117 | return;
|
---|
| 118 |
|
---|
| 119 | if ( fieldValue )
|
---|
| 120 | element.setAttribute( field.id, fieldValue );
|
---|
| 121 | else
|
---|
| 122 | element.removeAttribute( field.id );
|
---|
| 123 | };
|
---|
| 124 | }
|
---|
| 125 | }
|
---|
| 126 | } );
|
---|
| 127 | }
|
---|
| 128 |
|
---|
| 129 | /**
|
---|
| 130 | * Wrapping 'div' element around appropriate blocks among the selected ranges.
|
---|
| 131 | * @param {Object} editor
|
---|
| 132 | */
|
---|
| 133 | function createDiv( editor )
|
---|
| 134 | {
|
---|
| 135 | // new adding containers OR detected pre-existed containers.
|
---|
| 136 | var containers = [];
|
---|
| 137 | // node markers store.
|
---|
| 138 | var database = {};
|
---|
| 139 | // All block level elements which contained by the ranges.
|
---|
| 140 | var containedBlocks = [], block;
|
---|
| 141 |
|
---|
| 142 | // Get all ranges from the selection.
|
---|
| 143 | var selection = editor.document.getSelection(),
|
---|
| 144 | ranges = selection.getRanges();
|
---|
| 145 | var bookmarks = selection.createBookmarks();
|
---|
| 146 | var i, iterator;
|
---|
| 147 |
|
---|
| 148 | // Calcualte a default block tag if we need to create blocks.
|
---|
| 149 | var blockTag = editor.config.enterMode == CKEDITOR.ENTER_DIV ? 'div' : 'p';
|
---|
| 150 |
|
---|
| 151 | // collect all included elements from dom-iterator
|
---|
| 152 | for ( i = 0 ; i < ranges.length ; i++ )
|
---|
| 153 | {
|
---|
| 154 | iterator = ranges[ i ].createIterator();
|
---|
| 155 | while ( ( block = iterator.getNextParagraph() ) )
|
---|
| 156 | {
|
---|
| 157 | // include contents of blockLimit elements.
|
---|
| 158 | if ( block.getName() in divLimitDefinition )
|
---|
| 159 | {
|
---|
| 160 | var j, childNodes = block.getChildren();
|
---|
| 161 | for ( j = 0 ; j < childNodes.count() ; j++ )
|
---|
| 162 | addSafely( containedBlocks, childNodes.getItem( j ) , database );
|
---|
| 163 | }
|
---|
| 164 | else
|
---|
| 165 | {
|
---|
| 166 | // Bypass dtd disallowed elements.
|
---|
| 167 | while ( !dtd[ block.getName() ] && block.getName() != 'body' )
|
---|
| 168 | block = block.getParent();
|
---|
| 169 | addSafely( containedBlocks, block, database );
|
---|
| 170 | }
|
---|
| 171 | }
|
---|
| 172 | }
|
---|
| 173 |
|
---|
| 174 | CKEDITOR.dom.element.clearAllMarkers( database );
|
---|
| 175 |
|
---|
| 176 | var blockGroups = groupByDivLimit( containedBlocks );
|
---|
| 177 | var ancestor, blockEl, divElement;
|
---|
| 178 |
|
---|
| 179 | for ( i = 0 ; i < blockGroups.length ; i++ )
|
---|
| 180 | {
|
---|
| 181 | var currentNode = blockGroups[ i ][ 0 ];
|
---|
| 182 |
|
---|
| 183 | // Calculate the common parent node of all contained elements.
|
---|
| 184 | ancestor = currentNode.getParent();
|
---|
| 185 | for ( j = 1 ; j < blockGroups[ i ].length; j++ )
|
---|
| 186 | ancestor = ancestor.getCommonAncestor( blockGroups[ i ][ j ] );
|
---|
| 187 |
|
---|
| 188 | divElement = new CKEDITOR.dom.element( 'div', editor.document );
|
---|
| 189 |
|
---|
| 190 | // Normalize the blocks in each group to a common parent.
|
---|
| 191 | for ( j = 0; j < blockGroups[ i ].length ; j++ )
|
---|
| 192 | {
|
---|
| 193 | currentNode = blockGroups[ i ][ j ];
|
---|
| 194 |
|
---|
| 195 | while ( !currentNode.getParent().equals( ancestor ) )
|
---|
| 196 | currentNode = currentNode.getParent();
|
---|
| 197 |
|
---|
| 198 | // This could introduce some duplicated elements in array.
|
---|
| 199 | blockGroups[ i ][ j ] = currentNode;
|
---|
| 200 | }
|
---|
| 201 |
|
---|
| 202 | // Wrapped blocks counting
|
---|
| 203 | var fixedBlock = null;
|
---|
| 204 | for ( j = 0 ; j < blockGroups[ i ].length ; j++ )
|
---|
| 205 | {
|
---|
| 206 | currentNode = blockGroups[ i ][ j ];
|
---|
| 207 |
|
---|
| 208 | // Avoid DUP elements introduced by grouping.
|
---|
| 209 | if ( !( currentNode.getCustomData && currentNode.getCustomData( 'block_processed' ) ) )
|
---|
| 210 | {
|
---|
| 211 | currentNode.is && CKEDITOR.dom.element.setMarker( database, currentNode, 'block_processed', true );
|
---|
| 212 |
|
---|
| 213 | // Establish new container, wrapping all elements in this group.
|
---|
| 214 | if ( !j )
|
---|
| 215 | divElement.insertBefore( currentNode );
|
---|
| 216 |
|
---|
| 217 | divElement.append( currentNode );
|
---|
| 218 | }
|
---|
| 219 | }
|
---|
| 220 |
|
---|
| 221 | CKEDITOR.dom.element.clearAllMarkers( database );
|
---|
| 222 | containers.push( divElement );
|
---|
| 223 | }
|
---|
| 224 |
|
---|
| 225 | selection.selectBookmarks( bookmarks );
|
---|
| 226 | return containers;
|
---|
| 227 | }
|
---|
| 228 |
|
---|
| 229 | function getDiv( editor )
|
---|
| 230 | {
|
---|
| 231 | var path = new CKEDITOR.dom.elementPath( editor.getSelection().getStartElement() ),
|
---|
| 232 | blockLimit = path.blockLimit,
|
---|
| 233 | div = blockLimit && blockLimit.getAscendant( 'div', true );
|
---|
| 234 | return div;
|
---|
| 235 | }
|
---|
| 236 | /**
|
---|
| 237 | * Divide a set of nodes to different groups by their path's blocklimit element.
|
---|
| 238 | * Note: the specified nodes should be in source order naturally, which mean they are supposed to producea by following class:
|
---|
| 239 | * * CKEDITOR.dom.range.Iterator
|
---|
| 240 | * * CKEDITOR.dom.domWalker
|
---|
| 241 | * @return {Array []} the grouped nodes
|
---|
| 242 | */
|
---|
| 243 | function groupByDivLimit( nodes )
|
---|
| 244 | {
|
---|
| 245 | var groups = [],
|
---|
| 246 | lastDivLimit = null,
|
---|
| 247 | path, block;
|
---|
| 248 | for ( var i = 0 ; i < nodes.length ; i++ )
|
---|
| 249 | {
|
---|
| 250 | block = nodes[i];
|
---|
| 251 | var limit = getDivLimitElement( block );
|
---|
| 252 | if ( !limit.equals( lastDivLimit ) )
|
---|
| 253 | {
|
---|
| 254 | lastDivLimit = limit ;
|
---|
| 255 | groups.push( [] ) ;
|
---|
| 256 | }
|
---|
| 257 | groups[ groups.length - 1 ].push( block ) ;
|
---|
| 258 | }
|
---|
| 259 | return groups;
|
---|
| 260 | }
|
---|
| 261 |
|
---|
| 262 | // Synchronous field values to other impacted fields is required, e.g. div styles
|
---|
| 263 | // change should also alter inline-style text.
|
---|
| 264 | function commitInternally( targetFields )
|
---|
| 265 | {
|
---|
| 266 | var dialog = this.getDialog(),
|
---|
| 267 | element = dialog._element && dialog._element.clone()
|
---|
| 268 | || new CKEDITOR.dom.element( 'div', editor.document );
|
---|
| 269 |
|
---|
| 270 | // Commit this field and broadcast to target fields.
|
---|
| 271 | this.commit( element, true );
|
---|
| 272 |
|
---|
| 273 | targetFields = [].concat( targetFields );
|
---|
| 274 | var length = targetFields.length, field;
|
---|
| 275 | for ( var i = 0; i < length; i++ )
|
---|
| 276 | {
|
---|
| 277 | field = dialog.getContentElement.apply( dialog, targetFields[ i ].split( ':' ) );
|
---|
| 278 | field && field.setup && field.setup( element, true );
|
---|
| 279 | }
|
---|
| 280 | }
|
---|
| 281 |
|
---|
| 282 |
|
---|
| 283 | // Registered 'CKEDITOR.style' instances.
|
---|
| 284 | var styles = {} ;
|
---|
| 285 | /**
|
---|
| 286 | * Hold a collection of created block container elements.
|
---|
| 287 | */
|
---|
| 288 | var containers = [];
|
---|
| 289 | /**
|
---|
| 290 | * @type divDialog
|
---|
| 291 | */
|
---|
| 292 | return {
|
---|
| 293 | title : editor.lang.div.title,
|
---|
| 294 | minWidth : 400,
|
---|
| 295 | minHeight : 165,
|
---|
| 296 | contents :
|
---|
| 297 | [
|
---|
| 298 | {
|
---|
| 299 | id :'info',
|
---|
| 300 | label :editor.lang.common.generalTab,
|
---|
| 301 | title :editor.lang.common.generalTab,
|
---|
| 302 | elements :
|
---|
| 303 | [
|
---|
| 304 | {
|
---|
| 305 | type :'hbox',
|
---|
| 306 | widths : [ '50%', '50%' ],
|
---|
| 307 | children :
|
---|
| 308 | [
|
---|
| 309 | {
|
---|
| 310 | id :'elementStyle',
|
---|
| 311 | type :'select',
|
---|
| 312 | style :'width: 100%;',
|
---|
| 313 | label :editor.lang.div.styleSelectLabel,
|
---|
| 314 | 'default' : '',
|
---|
| 315 | // Options are loaded dynamically.
|
---|
| 316 | items :
|
---|
| 317 | [
|
---|
| 318 | [ editor.lang.common.notSet , '' ]
|
---|
| 319 | ],
|
---|
| 320 | onChange : function()
|
---|
| 321 | {
|
---|
| 322 | commitInternally.call( this, [ 'info:class', 'advanced:dir', 'advanced:style' ] );
|
---|
| 323 | },
|
---|
| 324 | setup : function( element )
|
---|
| 325 | {
|
---|
| 326 | for ( var name in styles )
|
---|
| 327 | styles[ name ].checkElementRemovable( element, true ) && this.setValue( name );
|
---|
| 328 | },
|
---|
| 329 | commit: function( element )
|
---|
| 330 | {
|
---|
| 331 | var styleName;
|
---|
| 332 | if ( ( styleName = this.getValue() ) )
|
---|
| 333 | {
|
---|
| 334 | var style = styles[ styleName ];
|
---|
| 335 | var customData = element.getCustomData( 'elementStyle' ) || '';
|
---|
| 336 |
|
---|
| 337 | style.applyToObject( element );
|
---|
| 338 | element.setCustomData( 'elementStyle', customData + style._.definition.attributes.style );
|
---|
| 339 | }
|
---|
| 340 | }
|
---|
| 341 | },
|
---|
| 342 | {
|
---|
| 343 | id :'class',
|
---|
| 344 | type :'text',
|
---|
| 345 | label :editor.lang.common.cssClass,
|
---|
| 346 | 'default' : ''
|
---|
| 347 | }
|
---|
| 348 | ]
|
---|
| 349 | }
|
---|
| 350 | ]
|
---|
| 351 | },
|
---|
| 352 | {
|
---|
| 353 | id :'advanced',
|
---|
| 354 | label :editor.lang.common.advancedTab,
|
---|
| 355 | title :editor.lang.common.advancedTab,
|
---|
| 356 | elements :
|
---|
| 357 | [
|
---|
| 358 | {
|
---|
| 359 | type :'vbox',
|
---|
| 360 | padding :1,
|
---|
| 361 | children :
|
---|
| 362 | [
|
---|
| 363 | {
|
---|
| 364 | type :'hbox',
|
---|
| 365 | widths : [ '50%', '50%' ],
|
---|
| 366 | children :
|
---|
| 367 | [
|
---|
| 368 | {
|
---|
| 369 | type :'text',
|
---|
| 370 | id :'id',
|
---|
| 371 | label :editor.lang.common.id,
|
---|
| 372 | 'default' : ''
|
---|
| 373 | },
|
---|
| 374 | {
|
---|
| 375 | type :'text',
|
---|
| 376 | id :'lang',
|
---|
| 377 | label :editor.lang.link.langCode,
|
---|
| 378 | 'default' : ''
|
---|
| 379 | }
|
---|
| 380 | ]
|
---|
| 381 | },
|
---|
| 382 | {
|
---|
| 383 | type :'hbox',
|
---|
| 384 | children :
|
---|
| 385 | [
|
---|
| 386 | {
|
---|
| 387 | type :'text',
|
---|
| 388 | id :'style',
|
---|
| 389 | style :'width: 100%;',
|
---|
| 390 | label :editor.lang.common.cssStyle,
|
---|
| 391 | 'default' : '',
|
---|
| 392 | commit : function( element )
|
---|
| 393 | {
|
---|
| 394 | // Merge with 'elementStyle', which is of higher priority.
|
---|
| 395 | var merged = this.getValue() + ( element.getCustomData( 'elementStyle' ) || '' );
|
---|
| 396 | element.setAttribute( 'style', merged );
|
---|
| 397 | }
|
---|
| 398 | }
|
---|
| 399 | ]
|
---|
| 400 | },
|
---|
| 401 | {
|
---|
| 402 | type :'hbox',
|
---|
| 403 | children :
|
---|
| 404 | [
|
---|
| 405 | {
|
---|
| 406 | type :'text',
|
---|
| 407 | id :'title',
|
---|
| 408 | style :'width: 100%;',
|
---|
| 409 | label :editor.lang.common.advisoryTitle,
|
---|
| 410 | 'default' : ''
|
---|
| 411 | }
|
---|
| 412 | ]
|
---|
| 413 | },
|
---|
| 414 | {
|
---|
| 415 | type :'select',
|
---|
| 416 | id :'dir',
|
---|
| 417 | style :'width: 100%;',
|
---|
| 418 | label :editor.lang.common.langDir,
|
---|
| 419 | 'default' : '',
|
---|
| 420 | items :
|
---|
| 421 | [
|
---|
| 422 | [ editor.lang.common.notSet , '' ],
|
---|
| 423 | [
|
---|
| 424 | editor.lang.common.langDirLtr,
|
---|
| 425 | 'ltr'
|
---|
| 426 | ],
|
---|
| 427 | [
|
---|
| 428 | editor.lang.common.langDirRtl,
|
---|
| 429 | 'rtl'
|
---|
| 430 | ]
|
---|
| 431 | ]
|
---|
| 432 | }
|
---|
| 433 | ]
|
---|
| 434 | }
|
---|
| 435 | ]
|
---|
| 436 | }
|
---|
| 437 | ],
|
---|
| 438 | onLoad : function()
|
---|
| 439 | {
|
---|
| 440 | setupFields.call( this );
|
---|
| 441 |
|
---|
| 442 | // Preparing for the 'elementStyle' field.
|
---|
| 443 | var dialog = this,
|
---|
| 444 | stylesField = this.getContentElement( 'info', 'elementStyle' );
|
---|
| 445 |
|
---|
| 446 | // Reuse the 'stylescombo' plugin's styles definition.
|
---|
| 447 | editor.getStylesSet( function( stylesDefinitions )
|
---|
| 448 | {
|
---|
| 449 | var styleName;
|
---|
| 450 |
|
---|
| 451 | if ( stylesDefinitions )
|
---|
| 452 | {
|
---|
| 453 | // Digg only those styles that apply to 'div'.
|
---|
| 454 | for ( var i = 0 ; i < stylesDefinitions.length ; i++ )
|
---|
| 455 | {
|
---|
| 456 | var styleDefinition = stylesDefinitions[ i ];
|
---|
| 457 | if ( styleDefinition.element && styleDefinition.element == 'div' )
|
---|
| 458 | {
|
---|
| 459 | styleName = styleDefinition.name;
|
---|
| 460 | styles[ styleName ] = new CKEDITOR.style( styleDefinition );
|
---|
| 461 |
|
---|
| 462 | // Populate the styles field options with style name.
|
---|
| 463 | stylesField.items.push( [ styleName, styleName ] );
|
---|
| 464 | stylesField.add( styleName, styleName );
|
---|
| 465 | }
|
---|
| 466 | }
|
---|
| 467 | }
|
---|
| 468 |
|
---|
| 469 | // We should disable the content element
|
---|
| 470 | // it if no options are available at all.
|
---|
| 471 | stylesField[ stylesField.items.length > 1 ? 'enable' : 'disable' ]();
|
---|
| 472 |
|
---|
| 473 | // Now setup the field value manually.
|
---|
| 474 | setTimeout( function() { stylesField.setup( dialog._element ); }, 0 );
|
---|
| 475 | } );
|
---|
| 476 | },
|
---|
| 477 | onShow : function()
|
---|
| 478 | {
|
---|
| 479 | // Whether always create new container regardless of existed
|
---|
| 480 | // ones.
|
---|
| 481 | if ( command == 'editdiv' )
|
---|
| 482 | {
|
---|
| 483 | // Try to discover the containers that already existed in
|
---|
| 484 | // ranges
|
---|
| 485 | var div = getDiv( editor );
|
---|
| 486 | // update dialog field values
|
---|
| 487 | div && this.setupContent( this._element = div );
|
---|
| 488 | }
|
---|
| 489 | },
|
---|
| 490 | onOk : function()
|
---|
| 491 | {
|
---|
| 492 | if ( command == 'editdiv' )
|
---|
| 493 | containers = [ this._element ];
|
---|
| 494 | else
|
---|
| 495 | containers = createDiv( editor, true );
|
---|
| 496 |
|
---|
| 497 | // Update elements attributes
|
---|
| 498 | var size = containers.length;
|
---|
| 499 | for ( var i = 0; i < size; i++ )
|
---|
| 500 | {
|
---|
| 501 | this.commitContent( containers[ i ] );
|
---|
| 502 |
|
---|
| 503 | // Remove empty 'style' attribute.
|
---|
| 504 | !containers[ i ].getAttribute( 'style' ) && containers[ i ].removeAttribute( 'style' );
|
---|
| 505 | }
|
---|
| 506 |
|
---|
| 507 | this.hide();
|
---|
| 508 | },
|
---|
| 509 | onHide : function()
|
---|
| 510 | {
|
---|
| 511 | // Remove style only when editing existing DIV. (#6315)
|
---|
| 512 | if ( command == 'editdiv' )
|
---|
| 513 | this._element.removeCustomData( 'elementStyle' );
|
---|
| 514 | delete this._element;
|
---|
| 515 | }
|
---|
| 516 | };
|
---|
| 517 | }
|
---|
| 518 |
|
---|
| 519 | CKEDITOR.dialog.add( 'creatediv', function( editor )
|
---|
| 520 | {
|
---|
| 521 | return divDialog( editor, 'creatediv' );
|
---|
| 522 | } );
|
---|
| 523 | CKEDITOR.dialog.add( 'editdiv', function( editor )
|
---|
| 524 | {
|
---|
| 525 | return divDialog( editor, 'editdiv' );
|
---|
| 526 | } );
|
---|
| 527 | } )();
|
---|
| 528 |
|
---|
| 529 | /*
|
---|
| 530 | * @name CKEDITOR.config.div_wrapTable
|
---|
| 531 | * Whether to wrap the whole table instead of indivisual cells when created 'div' in table cell.
|
---|
| 532 | * @type Boolean
|
---|
| 533 | * @default false
|
---|
| 534 | * @example config.div_wrapTable = true;
|
---|
| 535 | */
|
---|