瀏覽代碼

Fix: The multiple rowspanned cells prevents proper column insertion.

Maciej Gołaszewski 7 年之前
父節點
當前提交
8570731e7e
共有 2 個文件被更改,包括 43 次插入5 次删除
  1. 24 4
      packages/ckeditor5-table/src/tableutils.js
  2. 19 1
      packages/ckeditor5-table/tests/tableutils.js

+ 24 - 4
packages/ckeditor5-table/src/tableutils.js

@@ -142,20 +142,40 @@ export default class TableUtils extends Plugin {
 				writer.setAttribute( 'headingColumns', headingColumns + columns, table );
 			}
 
-			for ( const { column, cell: tableCell, colspan } of [ ...new TableWalker( table ) ] ) {
+			const tableMap = [ ...new TableWalker( table ) ];
+
+			// Holds row indexes of already analyzed row or rows that some rowspanned cell overlaps.
+			const skipRows = new Set();
+
+			for ( const { row, column, cell, colspan, rowspan } of tableMap ) {
+				if ( skipRows.has( row ) ) {
+					continue;
+				}
+
 				// Check if currently analyzed cell overlaps insert position.
 				const isBeforeInsertAt = column < insertAt;
 				const expandsOverInsertAt = column + colspan > insertAt;
 
 				if ( isBeforeInsertAt && expandsOverInsertAt ) {
 					// And if so expand that table cell.
-					writer.setAttribute( 'colspan', colspan + columns, tableCell );
+					writer.setAttribute( 'colspan', colspan + columns, cell );
+
+					// This cell will overlap cells in rows below so skip them.
+					if ( rowspan > 1 ) {
+						for ( let i = row; i < row + rowspan; i++ ) {
+							skipRows.add( i );
+						}
+					}
+
+					skipRows.add( row );
 				}
 
-				if ( column === insertAt ) {
-					const insertPosition = Position.createBefore( tableCell );
+				// The next cell might be not on the insertAt column - ie when there are many rowspanned cells before.
+				if ( column >= insertAt ) {
+					const insertPosition = Position.createBefore( cell );
 
 					createCells( columns, writer, insertPosition );
+					skipRows.add( row );
 				}
 			}
 		} );

+ 19 - 1
packages/ckeditor5-table/tests/tableutils.js

@@ -369,7 +369,7 @@ describe( 'TableUtils', () => {
 			], { headingColumns: 6 } ) );
 		} );
 
-		it( 'should skip row spanned cells', () => {
+		it( 'should skip row & column spanned cells', () => {
 			setData( model, modelTable( [
 				[ { colspan: 2, rowspan: 2, contents: '00[]' }, '02' ],
 				[ '12' ],
@@ -384,6 +384,24 @@ describe( 'TableUtils', () => {
 				[ '20', '', '', '21', '22' ]
 			], { headingColumns: 4 } ) );
 		} );
+
+		it( 'should properly insert column while table has rowspanned cells', () => {
+			setData( model, modelTable( [
+				[ { rowspan: 4, contents: '00[]' }, { rowspan: 2, contents: '01' }, '02' ],
+				[ '12' ],
+				[ { rowspan: 2, contents: '21' }, '22' ],
+				[ '32' ]
+			], { headingColumns: 2 } ) );
+
+			tableUtils.insertColumns( root.getNodeByPath( [ 0 ] ), { at: 1, columns: 1 } );
+
+			expect( formatTable( getData( model ) ) ).to.equal( formattedModelTable( [
+				[ { rowspan: 4, contents: '00[]' }, '', { rowspan: 2, contents: '01' }, '02' ],
+				[ '', '12' ],
+				[ '', { rowspan: 2, contents: '21' }, '22' ],
+				[ '', '32' ]
+			], { headingColumns: 3 } ) );
+		} );
 	} );
 
 	describe( 'splitCellHorizontally()', () => {