CLICK HERE TO BUY IT TODAY! OR GET IT FREE VIA TRIALPAY  

PHP Demo Application - Source Code

/Framework/Model/Vendor/CkEditor/_source/plugins/tabletools/plugin.js



/*
Copyright (c) 2003-2010, CKSource - Frederico Knabben. All rights reserved.
For licensing, see LICENSE.html or http://ckeditor.com/license
*/
(function()
{
	    function removeRawAttribute$nodeattr )
	    {
		        if ( CKEDITOR.env.ie )
		            $node.removeAttributeattr );
		        else
		            delete $nodeattr ];
		    }
	    var cellNodeRegex = /^(?:td|th)$/;
	    function getSelectedCellsselection )
	    {
		        // Walker will try to split text nodes, which will make the current selection
		        // invalid. So save bookmarks before doing anything.
		        var bookmarks selection.createBookmarks();
		        var ranges selection.getRanges();
		        var retval [];
		        var database {};
		        function moveOutOfCellGuardnode )
		        {
			            // Apply to the first cell only.
			            if ( retval.length )
			                return;
			            // If we are exiting from the first </td>, then the td should definitely be
			            // included.
			            if ( node.type == CKEDITOR.NODE_ELEMENT && cellNodeRegex.testnode.getName() )
			                    && !node.getCustomData'selected_cell' ) )
			            {
				                CKEDITOR.dom.element.setMarkerdatabasenode'selected_cell'true );
				                retval.pushnode );
				            }
			        }
		        for ( var ;
		 ranges.length ;
		 i++ )
		        {
			            var range ranges];
			            if ( range.collapsed )
			            {
				                // Walker does not handle collapsed ranges yet - fall back to old API.
				                var startNode range.getCommonAncestor();
				                var nearestCell startNode.getAscendant'td'true ) || startNode.getAscendant'th'true );
				                if ( nearestCell )
				                    retval.pushnearestCell );
				            }
			            else
			            {
				                var walker = new CKEDITOR.dom.walkerrange );
				                var node;
				                walker.guard moveOutOfCellGuard;
				                while ( ( node walker.next() ) )
				                {
					                    // If may be possible for us to have a range like this:
					                    // <td>^1</td><td>^2</td>
					                    // The 2nd td shouldn't be included.
					                    //
					                    // So we have to take care to include a td we've entered only when we've
					                    // walked into its children.
					                    var parent node.getParent();
					                    if ( parent && cellNodeRegex.testparent.getName() ) && !parent.getCustomData'selected_cell' ) )
					                    {
						                        CKEDITOR.dom.element.setMarkerdatabaseparent'selected_cell'true );
						                        retval.pushparent );
						                    }
					                }
				            }
			        }
		        CKEDITOR.dom.element.clearAllMarkersdatabase );
		        // Restore selection position.
		        selection.selectBookmarksbookmarks );
		        return retval;
		    }
	    function getFocusElementAfterDelCellscellsToDelete ) {
		        var 0,
		            last cellsToDelete.length 1,
		            database {},
		            cell,focusedCell,
		            tr;
		        while ( ( cell cellsToDeletei++ ] ) )
		            CKEDITOR.dom.element.setMarkerdatabasecell'delete_cell'true );
		        // 1.first we check left or right side focusable cell row by row;
		        0;
		        while ( ( cell cellsToDeletei++ ] ) )
		        {
			            if ( ( focusedCell cell.getPrevious() ) && !focusedCell.getCustomData'delete_cell' )
			              || ( focusedCell cell.getNext()     ) && !focusedCell.getCustomData'delete_cell' ) )
			            {
				                CKEDITOR.dom.element.clearAllMarkersdatabase );
				                return focusedCell;
				            }
			        }
		        CKEDITOR.dom.element.clearAllMarkersdatabase );
		        // 2. then we check the toppest row (outside the selection area square) focusable cell
		        tr cellsToDelete].getParent();
		        if ( ( tr tr.getPrevious() ) )
		            return tr.getLast();
		        // 3. last we check the lowerest  row focusable cell
		        tr cellsToDeletelast ].getParent();
		        if ( ( tr tr.getNext() ) )
		            return tr.getChild);
		        return null;
		    }
	    function clearRow$tr )
	    {
		        // Get the array of row's cells.
		        var $cells $tr.cells;
		        // Empty all cells.
		        for ( var ;
		 $cells.length ;
		 i++ )
		        {
			            $cells].innerHTML '';
			            if ( !CKEDITOR.env.ie )
			                ( new CKEDITOR.dom.element$cells] ) ).appendBogus();
			        }
		    }
	    function insertRowselectioninsertBefore )
	    {
		        // Get the row where the selection is placed in.
		        var row selection.getStartElement().getAscendant'tr' );
		        if ( !row )
		            return;
		        // Create a clone of the row.
		        var newRow row.clone( true );
		        insertBefore ?
		            newRow.insertBeforerow ) :
		            newRow.insertAfterrow );
		        // Clean the new row.
		        clearRownewRow.$ );
		    }
	    function deleteRowsselectionOrRow )
	    {
		        if ( selectionOrRow instanceof CKEDITOR.dom.selection )
		        {
			            var cells getSelectedCellsselectionOrRow ),
			                cellsCount cells.length,
			                rowsToDelete [],
			                cursorPosition,
			                previousRowIndex,
			                nextRowIndex;
			            // Queue up the rows - it's possible and likely that we have duplicates.
			            for ( var ;
			 cellsCount ;
			 i++ )
			            {
				                var row cells].getParent(),
				                        rowIndex row.$.rowIndex;
				                !&& ( previousRowIndex rowIndex );
				                rowsToDeleterowIndex ] = row;
				                == cellsCount && ( nextRowIndex rowIndex );
				            }
			            var table row.getAscendant'table' ),
			                    rows =  table.$.rows,
			                    rowCount rows.length;
			            // Where to put the cursor after rows been deleted?
			            // 1. Into next sibling row if any;
			            // 2. Into previous sibling row if any;
			            // 3. Into table's parent element if it's the very last row.
			            cursorPosition = new CKEDITOR.dom.element(
			                nextRowIndex rowCount && table.$.rowsnextRowIndex ] ||
			                previousRowIndex && table.$.rowspreviousRowIndex ] ||
			                table.$.parentNode );
			            for ( rowsToDelete.length ;
			 >= ;
			 i-- )
			            {
				                if ( rowsToDelete] )
				                    deleteRowsrowsToDelete] );
				            }
			            return cursorPosition;
			        }
		        else if ( selectionOrRow instanceof CKEDITOR.dom.element )
		        {
			            table selectionOrRow.getAscendant'table' );
			            if ( table.$.rows.length == )
			                table.remove();
			            else
			                selectionOrRow.remove();
			        }
		        return 0;
		    }
	    function insertColumnselectioninsertBefore )
	    {
		        // Get the cell where the selection is placed in.
		        var startElement selection.getStartElement();
		        var cell startElement.getAscendant'td'true ) || startElement.getAscendant'th'true );
		        if ( !cell )
		            return;
		        // Get the cell's table.
		        var table cell.getAscendant'table' );
		        var cellIndex cell.$.cellIndex;
		        // Loop through all rows available in the table.
		        for ( var ;
		 table.$.rows.length ;
		 i++ )
		        {
			            var $row table.$.rows];
			            // If the row doesn't have enough cells, ignore it.
			            if ( $row.cells.length < ( cellIndex ) )
			                continue;
			            cell = ( new CKEDITOR.dom.element$row.cellscellIndex ] ) ).clone( false );
			            if ( !CKEDITOR.env.ie )
			                cell.appendBogus();
			            // Get back the currently selected cell.
			            var baseCell = new CKEDITOR.dom.element$row.cellscellIndex ] );
			            if ( insertBefore )
			                cell.insertBeforebaseCell );
			            else
			                cell.insertAfterbaseCell );
			        }
		    }
	    function getFocusElementAfterDelColscells )
	    {
		        var cellIndexList [],
		            table cells] && cells].getAscendant'table' ),
		            ilength,
		            targetIndextargetCell;
		        // get the cellIndex list of delete cells
		        for ( 0length cells.length;
		 length;
		 i++ )
		            cellIndexList.pushcells[i].$.cellIndex );
		        // get the focusable column index
		        cellIndexList.sort();
		        for ( 1length cellIndexList.length;
		 length;
		 i++ )
		        {
			            if ( cellIndexList] - cellIndexList] > )
			            {
				                targetIndex cellIndexList] + 1;
				                break;
				            }
			        }
		        if ( !targetIndex )
		            targetIndex cellIndexList] > ? ( cellIndexList] - )
		                            : ( cellIndexListcellIndexList.length ] + );
		        // scan row by row to get the target cell
		        var rows table.$.rows;
		        for ( 0length rows.length;
		 length ;
		 i++ )
		        {
			            targetCell rows].cellstargetIndex ];
			            if ( targetCell )
			                break;
			        }
		        return targetCell ?  new CKEDITOR.dom.elementtargetCell ) :  table.getPrevious();
		    }
	    function deleteColumnsselectionOrCell )
	    {
		        if ( selectionOrCell instanceof CKEDITOR.dom.selection )
		        {
			            var colsToDelete getSelectedCellsselectionOrCell ),
			                elementToFocus getFocusElementAfterDelColscolsToDelete );
			            for ( var colsToDelete.length ;
			 >= ;
			 i-- )
			            {
				                if ( colsToDelete] )
				                    deleteColumnscolsToDelete] );
				            }
			            return elementToFocus;
			        }
		        else if ( selectionOrCell instanceof CKEDITOR.dom.element )
		        {
			            // Get the cell's table.
			            var table selectionOrCell.getAscendant'table' );
			            if ( !table )
			                return null;
			            // Get the cell index.
			            var cellIndex selectionOrCell.$.cellIndex;
			            /*
			             * Loop through all rows from down to up, coz it's possible that some rows
			             * will be deleted.
			             */
			            for ( table.$.rows.length ;
			 >= ;
			 i-- )
			            {
				                // Get the row.
				                var row = new CKEDITOR.dom.elementtable.$.rows] );
				                // If the cell to be removed is the first one and the row has just one cell.
				                if ( !cellIndex && row.$.cells.length == )
				                {
					                    deleteRowsrow );
					                    continue;
					                }
				                // Else, just delete the cell.
				                if ( row.$.cellscellIndex ] )
				                    row.$.removeChildrow.$.cellscellIndex ] );
				            }
			        }
		        return null;
		    }
	    function insertCellselectioninsertBefore )
	    {
		        var startElement selection.getStartElement();
		        var cell startElement.getAscendant'td'true ) || startElement.getAscendant'th'true );
		        if ( !cell )
		            return;
		        // Create the new cell element to be added.
		        var newCell cell.clone();
		        if ( !CKEDITOR.env.ie )
		            newCell.appendBogus();
		        if ( insertBefore )
		            newCell.insertBeforecell );
		        else
		            newCell.insertAftercell );
		    }
	    function deleteCellsselectionOrCell )
	    {
		        if ( selectionOrCell instanceof CKEDITOR.dom.selection )
		        {
			            var cellsToDelete getSelectedCellsselectionOrCell );
			            var table cellsToDelete] && cellsToDelete].getAscendant'table' );
			            var cellToFocus   getFocusElementAfterDelCellscellsToDelete );
			            for ( var cellsToDelete.length ;
			 >= ;
			 i-- )
			                deleteCellscellsToDelete] );
			            if ( cellToFocus )
			                placeCursorInCellcellToFocustrue );
			            else if ( table )
			                table.remove();
			        }
		        else if ( selectionOrCell instanceof CKEDITOR.dom.element )
		        {
			            var tr selectionOrCell.getParent();
			            if ( tr.getChildCount() == )
			                tr.remove();
			            else
			                selectionOrCell.remove();
			        }
		    }
	    // Remove filler at end and empty spaces around the cell content.
	    function trimCellcell )
	    {
		        var bogus cell.getBogus();
		        bogus && bogus.remove();
		        cell.trim();
		    }
	    function placeCursorInCellcellplaceAtEnd )
	    {
		        var range = new CKEDITOR.dom.rangecell.getDocument() );
		        if ( !range'moveToElementEdit' + ( placeAtEnd 'End' 'Start' ) ]( cell ) )
		        {
			            range.selectNodeContentscell );
			            range.collapseplaceAtEnd false true );
			        }
		        range.selecttrue );
		    }
	    function cellInRowtableMaprowIndexcell )
	    {
		        var oRow tableMaprowIndex ];
		        if ( typeof cell == 'undefined' )
		            return oRow;
		        for ( var ;
		 oRow && oRow.length ;
		 c++ )
		        {
			            if ( cell.is && oRow[c] == cell.$ )
			                return c;
			            else if ( == cell )
			                return new CKEDITOR.dom.elementoRow] );
			        }
		        return cell.is ? -null;
		    }
	    function cellInColtableMapcolIndexcell )
	    {
		        var oCol [];
		        for ( var 0;
		 tableMap.length;
		 r++ )
		        {
			            var row tableMap];
			            if ( typeof cell == 'undefined' )
			                oCol.pushrowcolIndex ] );
			            else if ( cell.is && rowcolIndex ] == cell.$ )
			                return r;
			            else if ( == cell )
			                return new CKEDITOR.dom.elementrowcolIndex ] );
			        }
		        return ( typeof cell == 'undefined' )? oCol cell.is ? -:  null;
		    }
	    function mergeCellsselectionmergeDirectionisDetect )
	    {
		        var cells getSelectedCellsselection );
		        // Invalid merge request if:
		        // 1. In batch mode despite that less than two selected.
		        // 2. In solo mode while not exactly only one selected.
		        // 3. Cells distributed in different table groups (e.g. from both thead and tbody).
		        var commonAncestor;
		        if ( ( mergeDirection cells.length != cells.length )
		                || ( commonAncestor selection.getCommonAncestor() )
		                && commonAncestor.type == CKEDITOR.NODE_ELEMENT
		                && commonAncestor.is'table' ) )
		        {
			            return false;
			        }
		        var    cell,
		            firstCell cells],
		            table firstCell.getAscendant'table' ),
		            map CKEDITOR.tools.buildTableMaptable ),
		            mapHeight map.length,
		            mapWidth map].length,
		            startRow firstCell.getParent().$.rowIndex,
		            startColumn cellInRowmapstartRowfirstCell );
		        if ( mergeDirection )
		        {
			            var targetCell;
			            try
			            {
				                targetCell =
				                    mapmergeDirection == 'up' ?
				                            ( startRow ):
				                            mergeDirection == 'down' ? ( startRow ) : startRow  ] [
				                         mergeDirection == 'left' ?
				                            ( startColumn ):
				                         mergeDirection == 'right' ?  ( startColumn ) : startColumn ];
				            }
			            catch( er )
			            {
				                return false;
				            }
			            // 1. No cell could be merged.
			            // 2. Same cell actually.
			            if ( !targetCell || firstCell.$ == targetCell  )
			                return false;
			            // Sort in map order regardless of the DOM sequence.
			            cells[ ( mergeDirection == 'up' || mergeDirection == 'left' ) ?
			                     'unshift' 'push' ]( new CKEDITOR.dom.elementtargetCell ) );
			        }
		        // Start from here are merging way ignorance (merge up/right, batch merge).
		        var    doc firstCell.getDocument(),
		            lastRowIndex startRow,
		            totalRowSpan 0,
		            totalColSpan 0,
		            // Use a documentFragment as buffer when appending cell contents.
		            frag = !isDetect && new CKEDITOR.dom.documentFragmentdoc ),
		            dimension 0;
		        for ( var 0;
		 cells.length;
		 i++ )
		        {
			            cell cells];
			            var tr cell.getParent(),
			                cellFirstChild cell.getFirst(),
			                colSpan cell.$.colSpan,
			                rowSpan cell.$.rowSpan,
			                rowIndex tr.$.rowIndex,
			                colIndex cellInRowmaprowIndexcell );
			            // Accumulated the actual places taken by all selected cells.
			            dimension += colSpan rowSpan;
			            // Accumulated the maximum virtual spans from column and row.
			            totalColSpan Math.maxtotalColSpancolIndex startColumn colSpan ) ;
			            totalRowSpan Math.maxtotalRowSpanrowIndex startRow rowSpan );
			            if ( !isDetect )
			            {
				                // Trim all cell fillers and check to remove empty cells.
				                if ( trimCellcell ), cell.getChildren().count() )
				                {
					                    // Merge vertically cells as two separated paragraphs.
					                    if ( rowIndex != lastRowIndex
					                        && cellFirstChild
					                        && !( cellFirstChild.isBlockBoundary
					                              && cellFirstChild.isBlockBoundary( { br 1
						} ) ) )
					                    {
						                        var last frag.getLastCKEDITOR.dom.walker.whitespacestrue ) );
						                        if ( last && !( last.is && last.is'br' ) ) )
						                            frag.append( new CKEDITOR.dom.element'br' ) );
						                    }
					                    cell.moveChildrenfrag );
					                }
				                cell.remove() : cell.setHtml'' );
				            }
			            lastRowIndex rowIndex;
			        }
		        if ( !isDetect )
		        {
			            frag.moveChildrenfirstCell );
			            if ( !CKEDITOR.env.ie )
			                firstCell.appendBogus();
			            if ( totalColSpan >= mapWidth )
			                firstCell.removeAttribute'rowSpan' );
			            else
			                firstCell.$.rowSpan totalRowSpan;
			            if ( totalRowSpan >= mapHeight )
			                firstCell.removeAttribute'colSpan' );
			            else
			                firstCell.$.colSpan totalColSpan;
			            // Swip empty <tr> left at the end of table due to the merging.
			            var trs = new CKEDITOR.dom.nodeListtable.$.rows ),
			                count trs.count();
			            for ( count 1;
			 >= 0;
			 i-- )
			            {
				                var tailTr trs.getItem);
				                if ( !tailTr.$.cells.length )
				                {
					                    tailTr.remove();
					                    count++;
					                    continue;
					                }
				            }
			            return firstCell;
			        }
		        // Be able to merge cells only if actual dimension of selected
		        // cells equals to the caculated rectangle.
		        else
		            return ( totalRowSpan totalColSpan ) == dimension;
		    }
	    function verticalSplitCell selectionisDetect )
	    {
		        var cells getSelectedCellsselection );
		        if ( cells.length )
		            return false;
		        else if ( isDetect )
		            return true;
		        var cell cells],
		            tr cell.getParent(),
		            table tr.getAscendant'table' ),
		            map CKEDITOR.tools.buildTableMaptable ),
		            rowIndex tr.$.rowIndex,
		            colIndex cellInRowmaprowIndexcell ),
		            rowSpan cell.$.rowSpan,
		            newCell,
		            newRowSpan,
		            newCellRowSpan,
		            newRowIndex;
		        if ( rowSpan )
		        {
			            newRowSpan Math.ceilrowSpan );
			            newCellRowSpan Math.floorrowSpan );
			            newRowIndex rowIndex newRowSpan;
			            var newCellTr = new CKEDITOR.dom.elementtable.$.rowsnewRowIndex ] ),
			                newCellRow cellInRowmapnewRowIndex ),
			                candidateCell;
			            newCell cell.clone();
			            // Figure out where to insert the new cell by checking the vitual row.
			            for ( var 0;
			 newCellRow.length;
			 c++ )
			            {
				                candidateCell newCellRow];
				                // Catch first cell actually following the column.
				                if ( candidateCell.parentNode == newCellTr.$
				                    && colIndex )
				                {
					                    newCell.insertBefore( new CKEDITOR.dom.elementcandidateCell ) );
					                    break;
					                }
				                else
				                    candidateCell null;
				            }
			            // The destination row is empty, append at will.
			            if ( !candidateCell )
			                newCellTr.appendnewCelltrue );
			        }
		        else
		        {
			            newCellRowSpan newRowSpan 1;
			            newCellTr tr.clone();
			            newCellTr.insertAftertr );
			            newCellTr.appendnewCell cell.clone() );
			            var cellsInSameRow cellInRowmaprowIndex );
			            for ( var 0;
			 cellsInSameRow.length;
			 i++ )
			                cellsInSameRow].rowSpan++;
			        }
		        if ( !CKEDITOR.env.ie )
		            newCell.appendBogus();
		        cell.$.rowSpan newRowSpan;
		        newCell.$.rowSpan newCellRowSpan;
		        if ( newRowSpan == )
		            cell.removeAttribute'rowSpan' );
		        if ( newCellRowSpan == )
		            newCell.removeAttribute'rowSpan' );
		        return newCell;
		    }
	    function horizontalSplitCellselectionisDetect )
	    {
		        var cells getSelectedCellsselection );
		        if ( cells.length )
		            return false;
		        else if ( isDetect )
		            return true;
		        var cell cells],
		            tr cell.getParent(),
		            table tr.getAscendant'table' ),
		            map CKEDITOR.tools.buildTableMaptable ),
		            rowIndex tr.$.rowIndex,
		            colIndex cellInRowmaprowIndexcell ),
		            colSpan cell.$.colSpan,
		            newCell,
		            newColSpan,
		            newCellColSpan;
		        if ( colSpan )
		        {
			            newColSpan Math.ceilcolSpan );
			            newCellColSpan Math.floorcolSpan );
			        }
		        else
		        {
			            newCellColSpan newColSpan 1;
			            var cellsInSameCol cellInColmapcolIndex );
			            for ( var 0;
			 cellsInSameCol.length;
			 i++ )
			                cellsInSameCol].colSpan++;
			        }
		        newCell cell.clone();
		        newCell.insertAftercell );
		        if ( !CKEDITOR.env.ie )
		            newCell.appendBogus();
		        cell.$.colSpan newColSpan;
		        newCell.$.colSpan newCellColSpan;
		        if ( newColSpan == )
		            cell.removeAttribute'colSpan' );
		        if ( newCellColSpan == )
		            newCell.removeAttribute'colSpan' );
		        return newCell;
		    }
	    // Context menu on table caption incorrect (#3834)
	    var contextMenuTags = { thead 1tbody 1tfoot 1td 1tr 1th 1
		};
	    CKEDITOR.plugins.tabletools =
	    {
		        init : function( editor )
		        {
			            var lang editor.lang.table;
			            editor.addCommand'cellProperties', new CKEDITOR.dialogCommand'cellProperties' ) );
			            CKEDITOR.dialog.add'cellProperties'this.path 'dialogs/tableCell.js' );
			            editor.addCommand'tableDelete',
			                {
				                    exec : function( editor )
				                    {
					                        var selection editor.getSelection();
					                        var startElement selection && selection.getStartElement();
					                        var table startElement && startElement.getAscendant'table'true );
					                        if ( !table )
					                            return;
					                        // Maintain the selection point at where the table was deleted.
					                        selection.selectElementtable );
					                        var range selection.getRanges()[0];
					                        range.collapse();
					                        selection.selectRanges( [ range ] );
					                        // If the table's parent has only one child, remove it,except body,as well.( #5416 )
					                        var parent table.getParent();
					                        if ( parent.getChildCount() == && parent.getName() != 'body' )
					                            parent.remove();
					                        else
					                            table.remove();
					                    }
				                } );
			            editor.addCommand'rowDelete',
			                {
				                    exec : function( editor )
				                    {
					                        var selection editor.getSelection();
					                        placeCursorInCelldeleteRowsselection ) );
					                    }
				                } );
			            editor.addCommand'rowInsertBefore',
			                {
				                    exec : function( editor )
				                    {
					                        var selection editor.getSelection();
					                        insertRowselectiontrue );
					                    }
				                } );
			            editor.addCommand'rowInsertAfter',
			                {
				                    exec : function( editor )
				                    {
					                        var selection editor.getSelection();
					                        insertRowselection );
					                    }
				                } );
			            editor.addCommand'columnDelete',
			                {
				                    exec : function( editor )
				                    {
					                        var selection editor.getSelection();
					                        var element deleteColumnsselection );
					                        element &&  placeCursorInCellelementtrue );
					                    }
				                } );
			            editor.addCommand'columnInsertBefore',
			                {
				                    exec : function( editor )
				                    {
					                        var selection editor.getSelection();
					                        insertColumnselectiontrue );
					                    }
				                } );
			            editor.addCommand'columnInsertAfter',
			                {
				                    exec : function( editor )
				                    {
					                        var selection editor.getSelection();
					                        insertColumnselection );
					                    }
				                } );
			            editor.addCommand'cellDelete',
			                {
				                    exec : function( editor )
				                    {
					                        var selection editor.getSelection();
					                        deleteCellsselection );
					                    }
				                } );
			            editor.addCommand'cellMerge',
			                {
				                    exec : function( editor )
				                    {
					                        placeCursorInCellmergeCellseditor.getSelection() ), true );
					                    }
				                } );
			            editor.addCommand'cellMergeRight',
			                {
				                    exec : function( editor )
				                    {
					                        placeCursorInCellmergeCellseditor.getSelection(), 'right' ), true );
					                    }
				                } );
			            editor.addCommand'cellMergeDown',
			                {
				                    exec : function( editor )
				                    {
					                        placeCursorInCellmergeCellseditor.getSelection(), 'down' ), true );
					                    }
				                } );
			            editor.addCommand'cellVerticalSplit',
			                {
				                    exec : function( editor )
				                    {
					                        placeCursorInCellverticalSplitCelleditor.getSelection() ) );
					                    }
				                } );
			            editor.addCommand'cellHorizontalSplit',
			                {
				                    exec : function( editor )
				                    {
					                        placeCursorInCellhorizontalSplitCelleditor.getSelection() ) );
					                    }
				                } );
			            editor.addCommand'cellInsertBefore',
			                {
				                    exec : function( editor )
				                    {
					                        var selection editor.getSelection();
					                        insertCellselectiontrue );
					                    }
				                } );
			            editor.addCommand'cellInsertAfter',
			                {
				                    exec : function( editor )
				                    {
					                        var selection editor.getSelection();
					                        insertCellselection );
					                    }
				                } );
			            // If the "menu" plugin is loaded, register the menu items.
			            if ( editor.addMenuItems )
			            {
				                editor.addMenuItems(
				                    {
					                        tablecell :
					                        {
						                            label lang.cell.menu,
						                            group 'tablecell',
						                            order 1,
						                            getItems : function()
						                            {
							                                var selection editor.getSelection(),
							                                    cells getSelectedCellsselection );
							                                return {
								                                    tablecell_insertBefore CKEDITOR.TRISTATE_OFF,
								                                    tablecell_insertAfter CKEDITOR.TRISTATE_OFF,
								                                    tablecell_delete CKEDITOR.TRISTATE_OFF,
								                                    tablecell_merge mergeCellsselectionnulltrue ) ? CKEDITOR.TRISTATE_OFF CKEDITOR.TRISTATE_DISABLED,
								                                    tablecell_merge_right mergeCellsselection'right'true ) ? CKEDITOR.TRISTATE_OFF CKEDITOR.TRISTATE_DISABLED,
								                                    tablecell_merge_down mergeCellsselection'down'true ) ? CKEDITOR.TRISTATE_OFF CKEDITOR.TRISTATE_DISABLED,
								                                    tablecell_split_vertical verticalSplitCellselectiontrue ) ? CKEDITOR.TRISTATE_OFF CKEDITOR.TRISTATE_DISABLED,
								                                    tablecell_split_horizontal horizontalSplitCellselectiontrue ) ? CKEDITOR.TRISTATE_OFF CKEDITOR.TRISTATE_DISABLED,
								                                    tablecell_properties cells.length CKEDITOR.TRISTATE_OFF CKEDITOR.TRISTATE_DISABLED
								                                };
							                            }
						                        },
					                        tablecell_insertBefore :
					                        {
						                            label lang.cell.insertBefore,
						                            group 'tablecell',
						                            command 'cellInsertBefore',
						                            order 5
						                        },
					                        tablecell_insertAfter :
					                        {
						                            label lang.cell.insertAfter,
						                            group 'tablecell',
						                            command 'cellInsertAfter',
						                            order 10
						                        },
					                        tablecell_delete :
					                        {
						                            label lang.cell.deleteCell,
						                            group 'tablecell',
						                            command 'cellDelete',
						                            order 15
						                        },
					                        tablecell_merge :
					                        {
						                            label lang.cell.merge,
						                            group 'tablecell',
						                            command 'cellMerge',
						                            order 16
						                        },
					                        tablecell_merge_right :
					                        {
						                            label lang.cell.mergeRight,
						                            group 'tablecell',
						                            command 'cellMergeRight',
						                            order 17
						                        },
					                        tablecell_merge_down :
					                        {
						                            label lang.cell.mergeDown,
						                            group 'tablecell',
						                            command 'cellMergeDown',
						                            order 18
						                        },
					                        tablecell_split_horizontal :
					                        {
						                            label lang.cell.splitHorizontal,
						                            group 'tablecell',
						                            command 'cellHorizontalSplit',
						                            order 19
						                        },
					                        tablecell_split_vertical :
					                        {
						                            label lang.cell.splitVertical,
						                            group 'tablecell',
						                            command 'cellVerticalSplit',
						                            order 20
						                        },
					                        tablecell_properties :
					                        {
						                            label lang.cell.title,
						                            group 'tablecellproperties',
						                            command 'cellProperties',
						                            order 21
						                        },
					                        tablerow :
					                        {
						                            label lang.row.menu,
						                            group 'tablerow',
						                            order 1,
						                            getItems : function()
						                            {
							                                return {
								                                    tablerow_insertBefore CKEDITOR.TRISTATE_OFF,
								                                    tablerow_insertAfter CKEDITOR.TRISTATE_OFF,
								                                    tablerow_delete CKEDITOR.TRISTATE_OFF
								                                };
							                            }
						                        },
					                        tablerow_insertBefore :
					                        {
						                            label lang.row.insertBefore,
						                            group 'tablerow',
						                            command 'rowInsertBefore',
						                            order 5
						                        },
					                        tablerow_insertAfter :
					                        {
						                            label lang.row.insertAfter,
						                            group 'tablerow',
						                            command 'rowInsertAfter',
						                            order 10
						                        },
					                        tablerow_delete :
					                        {
						                            label lang.row.deleteRow,
						                            group 'tablerow',
						                            command 'rowDelete',
						                            order 15
						                        },
					                        tablecolumn :
					                        {
						                            label lang.column.menu,
						                            group 'tablecolumn',
						                            order 1,
						                            getItems : function()
						                            {
							                                return {
								                                    tablecolumn_insertBefore CKEDITOR.TRISTATE_OFF,
								                                    tablecolumn_insertAfter CKEDITOR.TRISTATE_OFF,
								                                    tablecolumn_delete CKEDITOR.TRISTATE_OFF
								                                };
							                            }
						                        },
					                        tablecolumn_insertBefore :
					                        {
						                            label lang.column.insertBefore,
						                            group 'tablecolumn',
						                            command 'columnInsertBefore',
						                            order 5
						                        },
					                        tablecolumn_insertAfter :
					                        {
						                            label lang.column.insertAfter,
						                            group 'tablecolumn',
						                            command 'columnInsertAfter',
						                            order 10
						                        },
					                        tablecolumn_delete :
					                        {
						                            label lang.column.deleteColumn,
						                            group 'tablecolumn',
						                            command 'columnDelete',
						                            order 15
						                        }
					                    });
				            }
			            // If the "contextmenu" plugin is laoded, register the listeners.
			            if ( editor.contextMenu )
			            {
				                editor.contextMenu.addListener( function( elementselection )
				                    {
					                        if ( !element || element.isReadOnly() )
					                            return null;
					                        while ( element )
					                        {
						                            if ( element.getName() in contextMenuTags )
						                            {
							                                return {
								                                    tablecell CKEDITOR.TRISTATE_OFF,
								                                    tablerow CKEDITOR.TRISTATE_OFF,
								                                    tablecolumn CKEDITOR.TRISTATE_OFF
								                                };
							                            }
						                            element element.getParent();
						                        }
					                        return null;
					                    } );
				            }
			        },
		        getSelectedCells getSelectedCells
		    };
	    CKEDITOR.plugins.add'tabletools'CKEDITOR.plugins.tabletools );
	})();
/**
 * Create a two-dimension array that reflects the actual layout of table cells,
 * with cell spans, with mappings to the original td elements.
 * @param table {CKEDITOR.dom.element}
 */
CKEDITOR.tools.buildTableMap = function ( table )
{
	    var aRows table.$.rows ;
	    // Row and Column counters.
	    var = -;
	    var aMap [];
	    for ( var ;
	 aRows.length ;
	 i++ )
	    {
		        r++ ;
		        !aMap[r] && ( aMap[r] = [] );
		        var = -;
		        for ( var ;
		 aRows[i].cells.length ;
		 j++ )
		        {
			            var oCell aRows[i].cells[j] ;
			            c++ ;
			            while ( aMap[r][c] )
			                c++ ;
			            var iColSpan isNaNoCell.colSpan ) ? oCell.colSpan ;
			            var iRowSpan isNaNoCell.rowSpan ) ? oCell.rowSpan ;
			            for ( var rs ;
			 rs iRowSpan ;
			 rs++ )
			            {
				                if ( !aMap[rs] )
				                    aMap[rs] = [];
				                for ( var cs ;
				 cs iColSpan ;
				 cs++ )
				                {
					                    aMap[rs][cs] = aRows[i].cells[j] ;
					                }
				            }
			            += iColSpan ;
			        }
		    }
	    return aMap ;
	};





PHP Demo Source Code Index