Ticket #2767: 2767.patch

File 2767.patch, 7.4 KB (added by Garry Yao, 15 years ago)
  • _source/core/tools.js

     
    310310                                return i;
    311311                }
    312312                return -1;
     313        },
     314       
     315        /**
     316         * Find the deep-most common ancestor of a set of dom nodes.
     317         * Note: This method will never failed to found DCA since 'body' tag always there.
     318         * @param {Array}
     319         *            nodes The target set of nodes
     320         * @return {CKEDITOR.dom.node} The DCA result
     321         */
     322        getDCAOfNodes : function ( nodes )
     323        {
     324                var range , currentDCA;
     325
     326                while ( nodes.length > 1 )
     327                {
     328                        range = new CKEDITOR.dom.range();
     329                        range.startContainer = nodes[ 0 ];
     330                        range.endContainer = nodes[ 1 ];
     331                        currentDCA = range.getCommonAncestor( false );
     332                        if ( currentDCA.getName() === 'body' )
     333                                return currentDCA;
     334                        else
     335                                nodes.splice( 0 , 2 , [ currentDCA ] );
     336                }
     337                return nodes[ 0 ];
    313338        }
    314339};
    315340
  • _source/core/dom/text.js

     
    9797                                return this.$.nodeValue.substr( indexA );
    9898                        else
    9999                                return this.$.nodeValue.substring( indexA, indexB );
     100                },
     101                /**
     102                 * Whether this text node contain nothing but spaces.
     103                 * @return {Boolean}
     104                 */
     105                isEmpty : function ( )
     106                {
     107                        return CKEDITOR.tools.trim( this.getText() ).length === 0
    100108                }
    101109        });
  • _source/plugins/elementspath/plugin.js

     
    5353                        editor.on( 'selectionChange', function( ev )
    5454                                {
    5555                                        var env = CKEDITOR.env;
    56 
    57                                         var selection = ev.data.selection;
    58 
    59                                         var element = selection.getStartElement(),
     56                                       
     57                                        //The root node of this selection
     58                                        var root = ev.data.selection.getSelectionRootNode(),
    6059                                                html = [],
    6160                                                elementsList = this._.elementsPath.list = [];
    6261
    63                                         while ( element )
     62                                        while ( root )
    6463                                        {
    65                                                 var index = elementsList.push( element ) - 1;
     64                                                var index = elementsList.push( root ) - 1;
    6665                                                var name;
    67                                                 if ( element.getAttribute( '_cke_real_element_type' ) )
    68                                                         name = element.getAttribute( '_cke_real_element_type' );
     66                                                if ( root.getAttribute( '_cke_real_element_type' ) )
     67                                                        name = root.getAttribute( '_cke_real_element_type' );
    6968                                                else
    70                                                         name = element.getName();
     69                                                        name = root.getName();
    7170
    7271                                                // Use this variable to add conditional stuff to the
    7372                                                // HTML (because we are doing it in reverse order... unshift).
     
    9998                                                if ( name == 'body' )
    10099                                                        break;
    101100
    102                                                 element = element.getParent();
     101                                                root = root.getParent();
    103102                                        }
    104103
    105104                                        getSpaceElement().setHtml( html.join('') );
  • _source/plugins/selection/plugin.js

     
    2121                var firstElement = sel.getStartElement();
    2222                var currentPath = new CKEDITOR.dom.elementPath( firstElement );
    2323
    24                 if ( !currentPath.compare( this._.selectionPreviousPath ) )
    25                 {
    26                         this._.selectionPreviousPath = currentPath;
    27                         this.fire( 'selectionChange', { selection : sel, path : currentPath, element : firstElement } );
    28                 }
     24                this._.selectionPreviousPath = currentPath;
     25                this.fire( 'selectionChange', { selection : sel, path : currentPath, element : firstElement } );
    2926        };
    3027
    3128        var checkSelectionChangeTimer;
     
    635632                        }
    636633                        this.selectRanges( ranges );
    637634                        return this;
     635                },
     636               
     637                /**
     638                 * Get the root node of this selection, it represent the topmost node which
     639                 * contain the whole range.
     640                 *
     641                 * @return {CKEDITOR.dom.node} The root node of this selection
     642                 */
     643                getSelectionRootNode : function ( )
     644                {
     645                        var ranges , ancestors = [] , dca;
     646                        ranges = this.getRanges();
     647                        var i , l;
     648
     649                        if ( ranges.length == 1 && ranges[ 0 ].collapsed )
     650                                return this.getStartElement();
     651
     652                        for ( i = 0 ; i < length ; i++ )
     653                        {
     654                                ancestors.push( ranges[ i ].getCommonAncestor() );
     655                        }
     656                        return ( dca = CKEDITOR.tools.getDCAOfNodes( ancestors ) ).type === CKEDITOR.NODE_TEXT ? dca
     657                                        .getParent()
     658                                        : dca;
    638659                }
    639660        };
    640661})();
  • _source/plugins/styles/plugin.js

     
    4949
    5050                                        // Check the current state for the style defined for that
    5151                                        // callback.
    52                                         var currentState = callback.style.checkActive( ev.data.path ) ? CKEDITOR.TRISTATE_ON : CKEDITOR.TRISTATE_OFF;
     52                                        var currentState = callback.style.checkSelectionStyled( ev.data.selection ) ? CKEDITOR.TRISTATE_ON : CKEDITOR.TRISTATE_OFF;
    5353
    5454                                        // If the state changed since the last check.
    5555                                        if ( callback.state !== currentState )
     
    152152                        }
    153153                        return false;
    154154                },
     155               
     156                /**
     157                 * Check whether all the ranges within the specified selection is
     158                 * stained with the current style.
     159                 *
     160                 * @param {CKEDITOR.dom.selection}
     161                 *            selection
     162                 * @return {Boolean}
     163                 */
     164                checkSelectionStyled : function ( selection )
     165                {
     166                        var i , ranges = selection.getRanges() , l = ranges.length , isStyled = true;
     167                        // In search for a non-styled range
     168                        for ( i = 0 ; i < l ; i++ )
     169                        {
     170                                if ( !this.checkRangeStyled( ranges[ i ] ) )
     171                                {
     172                                        isStyled = false;
     173                                        break;
     174                                }
     175                        }
     176                        // Select a collapsed range cause IE move selection to the end of
     177                        // text nodes.
     178                        if ( !CKEDITOR.env.ie )
     179                                selection.selectRanges( ranges );
     180                        return isStyled;
     181                },
    155182
     183                /**
     184                 * Check whether all the text content of the specified range is stained
     185                 * with the current style.
     186                 *
     187                 * @param {CKEDITOR.dom.range}
     188                 *            range
     189                 * @return {Boolean}
     190                 */
     191                checkRangeStyled : function ( range )
     192                {
     193
     194                        if ( range.collapsed )
     195                                return this.checkActive( new CKEDITOR.dom.elementPath(
     196                                                range.startContainer ) );
     197
     198                        var bookmark = range.createBookmark() , startNode = bookmark.startNode , endNode = bookmark.endNode;
     199
     200                        // Start from first node within range
     201                        var walker = new CKEDITOR.dom.domWalker( startNode.getNextSourceNode() ) , isStyled = true , self = this;
     202
     203                        // DFS forward in searching for text nodes within the range.
     204                        walker.forward( function ( walkerEvt )
     205                        {
     206                                var currentNode = walkerEvt.data.from;
     207                                if ( currentNode.equals( startNode ) )
     208                                        return;
     209                                else if ( currentNode.equals( endNode ) )
     210                                        // Stop after the end node.
     211                                        this.stop();
     212                                else if ( currentNode.type === CKEDITOR.NODE_TEXT
     213                                                && !currentNode.isEmpty()
     214                                                && !self.checkActive( new CKEDITOR.dom.elementPath(
     215                                                                currentNode ) ) )
     216                                // stop when we found the first non-styled non-empty text
     217                                // node
     218                                {
     219                                        isStyled = false;
     220                                        this.stop();
     221                                }
     222                        } );
     223
     224                        range.moveToBookmark( bookmark );
     225                        return isStyled;
     226                },
     227
    156228                // Checks if an element, or any of its attributes, is removable by the
    157229                // current style definition.
    158230                checkElementRemovable : function( element, fullMatch )
© 2003 – 2022, CKSource sp. z o.o. sp.k. All rights reserved. | Terms of use | Privacy policy