From: Derk-Jan Hartman Date: Sat, 30 Nov 2013 17:14:31 +0000 (+0100) Subject: jquery.tablesorter: Use data() instead of DOM Node properties X-Git-Tag: 1.31.0-rc.0~13207^2 X-Git-Url: http://git.cyclocoop.org/%40spipnet%40?a=commitdiff_plain;h=e8cca377c1056a5d1a3935ddb48c010538ccabf6;p=lhc%2Fweb%2Fwiklou.git jquery.tablesorter: Use data() instead of DOM Node properties Change-Id: I5fe512c606c5c3ee96abb16185f349b5d8241c1f --- diff --git a/resources/src/jquery/jquery.tablesorter.js b/resources/src/jquery/jquery.tablesorter.js index e798cc971e..f3f2655047 100644 --- a/resources/src/jquery/jquery.tablesorter.js +++ b/resources/src/jquery/jquery.tablesorter.js @@ -183,7 +183,8 @@ var i, j, $row, cols, totalRows = ( table.tBodies[0] && table.tBodies[0].rows.length ) || 0, totalCells = ( table.tBodies[0].rows[0] && table.tBodies[0].rows[0].cells.length ) || 0, - parsers = table.config.parsers, + config = $( table ).data( 'tablesorter' ).config, + parsers = config.parsers, cache = { row: [], normalized: [] @@ -197,7 +198,7 @@ // if this is a child row, add it to the last row's children and // continue to the next row - if ( $row.hasClass( table.config.cssChildRow ) ) { + if ( $row.hasClass( config.cssChildRow ) ) { cache.row[cache.row.length - 1] = cache.row[cache.row.length - 1].add( $row ); // go to the next for loop continue; @@ -279,10 +280,12 @@ } function buildHeaders( table, msg ) { - var maxSeen = 0, + var config = $( table ).data( 'tablesorter' ).config, + maxSeen = 0, colspanOffset = 0, columns, i, + $cell, rowspan, colspan, headerCount, @@ -335,30 +338,31 @@ // as each header can span over multiple columns (using colspan=N), // we have to bidirectionally map headers to their columns and columns to their headers - table.headerToColumns = []; - table.columnToHeader = []; - $tableHeaders.each( function ( headerIndex ) { + $cell = $(this); columns = []; + for ( i = 0; i < this.colSpan; i++ ) { - table.columnToHeader[ colspanOffset + i ] = headerIndex; + config.columnToHeader[ colspanOffset + i ] = headerIndex; columns.push( colspanOffset + i ); } - table.headerToColumns[ headerIndex ] = columns; + config.headerToColumns[ headerIndex ] = columns; colspanOffset += this.colSpan; - this.headerIndex = headerIndex; - this.order = 0; - this.count = 0; + $cell.data( { + headerIndex: headerIndex, + order: 0, + count: 0 + }); - if ( $( this ).hasClass( table.config.unsortableClass ) ) { - this.sortDisabled = true; + if ( $cell.hasClass( config.unsortableClass ) ) { + $cell.data( 'sortDisabled', true ); } - if ( !this.sortDisabled ) { - $( this ) - .addClass( table.config.cssHeader ) + if ( !$cell.data( 'sortDisabled' ) ) { + $cell + .addClass( config.cssHeader ) .prop( 'tabIndex', 0 ) .attr( { role: 'columnheader button', @@ -367,7 +371,7 @@ } // add cell to headerList - table.config.headerList[headerIndex] = this; + config.headerList[headerIndex] = this; } ); return $tableHeaders; @@ -387,18 +391,23 @@ $.each( headerToColumns, function ( headerIndex, columns ) { $.each( columns, function ( i, columnIndex ) { - var header = $headers[headerIndex]; + var header = $headers[headerIndex], + $header = $( header ); if ( !isValueInArray( columnIndex, sortList ) ) { // Column shall not be sorted: Reset header count and order. - header.order = 0; - header.count = 0; + $header.data( { + order: 0, + count: 0 + } ); } else { // Column shall be sorted: Apply designated count and order. $.each( sortList, function ( j, sortColumn ) { if ( sortColumn[0] === i ) { - header.order = sortColumn[1]; - header.count = sortColumn[1] + 1; + $header.data( { + order: sortColumn[1], + count: sortColumn[1] + 1 + } ); return false; } } ); @@ -541,7 +550,7 @@ */ function explodeRowspans( $table ) { var spanningRealCellIndex, rowSpan, colSpan, - cell, i, $tds, $clone, $nextRows, + cell, cellData, i, $tds, $clone, $nextRows, rowspanCells = $table.find( '> tbody > tr > [rowspan]' ).get(); // Short circuit @@ -557,8 +566,10 @@ col = 0, l = this.cells.length; for ( i = 0; i < l; i++ ) { - this.cells[i].realCellIndex = col; - this.cells[i].realRowIndex = this.rowIndex; + $( this.cells[i] ).data( 'tablesorter', { + realCellIndex: col, + realRowIndex: this.rowIndex + } ); col += this.cells[i].colSpan; } } ); @@ -568,45 +579,55 @@ // Re-sort whenever a rowspanned cell's realCellIndex is changed, because it // might change the sort order. function resortCells() { + var cellAData, + cellBData, + ret; rowspanCells = rowspanCells.sort( function ( a, b ) { - var ret = a.realCellIndex - b.realCellIndex; + cellAData = $.data( a, 'tablesorter' ); + cellBData = $.data( b, 'tablesorter' ); + ret = cellAData.realCellIndex - cellBData.realCellIndex; if ( !ret ) { - ret = a.realRowIndex - b.realRowIndex; + ret = cellAData.realRowIndex - cellBData.realRowIndex; } return ret; } ); $.each( rowspanCells, function () { - this.needResort = false; + $.data( this, 'tablesorter' ).needResort = false; } ); } resortCells(); function filterfunc() { - return this.realCellIndex >= spanningRealCellIndex; + return $.data( this, 'tablesorter' ).realCellIndex >= spanningRealCellIndex; } function fixTdCellIndex() { - this.realCellIndex += colSpan; + $.data( this, 'tablesorter' ).realCellIndex += colSpan; if ( this.rowSpan > 1 ) { - this.needResort = true; + $.data( this, 'tablesorter' ).needResort = true; } } while ( rowspanCells.length ) { - if ( rowspanCells[0].needResort ) { + if ( $.data( rowspanCells[0], 'tablesorter' ).needResort ) { resortCells(); } cell = rowspanCells.shift(); + cellData = $.data( cell, 'tablesorter' ); rowSpan = cell.rowSpan; colSpan = cell.colSpan; - spanningRealCellIndex = cell.realCellIndex; + spanningRealCellIndex = cellData.realCellIndex; cell.rowSpan = 1; $nextRows = $( cell ).parent().nextAll(); for ( i = 0; i < rowSpan - 1; i++ ) { $tds = $( $nextRows[i].cells ).filter( filterfunc ); $clone = $( cell ).clone(); - $clone[0].realCellIndex = spanningRealCellIndex; + $clone.data( 'tablesorter', { + realCellIndex: spanningRealCellIndex, + realRowIndex: cellData.realRowIndex + i, + needResort: true + } ); if ( $tds.length ) { $tds.each( fixTdCellIndex ); $tds.first().before( $clone ); @@ -698,7 +719,9 @@ parsers: {}, cancelSelection: true, sortList: [], - headerList: [] + headerList: [], + headerToColumns: [], + columnToHeader: [] }, dateRegex: [], @@ -731,17 +754,13 @@ } $table.addClass( 'jquery-tablesorter' ); - // FIXME config should probably not be stored in the plain table node - // New config object. - table.config = {}; - - // Merge and extend. - config = $.extend( table.config, $.tablesorter.defaultOptions, settings ); + // Merge and extend + config = $.extend( {}, $.tablesorter.defaultOptions, settings ); // Save the settings where they read $.data( table, 'tablesorter', { config: config } ); - // Get the CSS class names, could be done else where. + // Get the CSS class names, could be done elsewhere sortCSS = [ config.cssDesc, config.cssAsc ]; sortMsg = [ mw.msg( 'sort-descending' ), mw.msg( 'sort-ascending' ) ]; @@ -781,14 +800,14 @@ explodeRowspans( $table ); - // try to auto detect column type, and store in tables config - table.config.parsers = buildParserCache( table, $headers ); + // Try to auto detect column type, and store in tables config + config.parsers = buildParserCache( table, $headers ); } // Apply event handling to headers // this is too big, perhaps break it out? - $headers.not( '.' + table.config.unsortableClass ).on( 'keypress click', function ( e ) { - var cell, columns, newSortList, i, + $headers.not( '.' + config.unsortableClass ).on( 'keypress click', function ( e ) { + var cell, $cell, columns, newSortList, i, totalRows, j, s, o; @@ -817,16 +836,21 @@ totalRows = ( $table[0].tBodies[0] && $table[0].tBodies[0].rows.length ) || 0; if ( !table.sortDisabled && totalRows > 0 ) { + cell = this; + $cell = $( cell ); + // Get current column sort order - this.order = this.count % 2; - this.count++; + $cell.data( { + order: $cell.data( 'count' ) % 2, + count: $cell.data( 'count' ) + 1 + } ); cell = this; // Get current column index - columns = table.headerToColumns[ this.headerIndex ]; + columns = config.headerToColumns[ $cell.data( 'headerIndex' ) ]; newSortList = $.map( columns, function ( c ) { // jQuery "helpfully" flattens the arrays... - return [[c, cell.order]]; + return [[c, $cell.data( 'order' )]]; } ); // Index of first column belonging to this header i = columns[0]; @@ -846,9 +870,8 @@ s = config.sortList[j]; o = config.headerList[s[0]]; if ( isValueInArray( s[0], newSortList ) ) { - o.count = s[1]; - o.count++; - s[1] = o.count % 2; + $(o).data( 'count', s[1] + 1 ); + s[1] = $( o ).data( 'count' ) % 2; } } } else { @@ -858,10 +881,10 @@ } // Reset order/counts of cells not affected by sorting - setHeadersOrder( $headers, config.sortList, table.headerToColumns ); + setHeadersOrder( $headers, config.sortList, config.headerToColumns ); // Set CSS for headers - setHeadersCss( $table[0], $headers, config.sortList, sortCSS, sortMsg, table.columnToHeader ); + setHeadersCss( $table[0], $headers, config.sortList, sortCSS, sortMsg, config.columnToHeader ); appendToTable( $table[0], multisort( $table[0], config.sortList, cache ) ); @@ -902,13 +925,13 @@ // Set each column's sort count to be able to determine the correct sort // order when clicking on a header cell the next time - setHeadersOrder( $headers, sortList, table.headerToColumns ); + setHeadersOrder( $headers, sortList, config.headerToColumns ); // re-build the cache for the tbody cells cache = buildCache( table ); // set css for headers - setHeadersCss( table, $headers, sortList, sortCSS, sortMsg, table.columnToHeader ); + setHeadersCss( table, $headers, sortList, sortCSS, sortMsg, config.columnToHeader ); // sort the table and append it to the dom appendToTable( table, multisort( table, sortList, cache ) ); diff --git a/tests/qunit/suites/resources/jquery/jquery.tablesorter.test.js b/tests/qunit/suites/resources/jquery/jquery.tablesorter.test.js index 92dad9ffcf..5464d2220e 100644 --- a/tests/qunit/suites/resources/jquery/jquery.tablesorter.test.js +++ b/tests/qunit/suites/resources/jquery/jquery.tablesorter.test.js @@ -1160,11 +1160,11 @@ '' ); $table.tablesorter(); - assert.equal( $table.find( '#A2' ).prop( 'headerIndex' ), + assert.equal( $table.find( '#A2' ).data( 'headerIndex' ), undefined, 'A2 should not be a sort header' ); - assert.equal( $table.find( '#C1' ).prop( 'headerIndex' ), + assert.equal( $table.find( '#C1' ).data( 'headerIndex' ), 2, 'C1 should be a sort header' ); @@ -1181,11 +1181,11 @@ '' ); $table.tablesorter(); - assert.equal( $table.find( '#C2' ).prop( 'headerIndex' ), + assert.equal( $table.find( '#C2' ).data( 'headerIndex' ), 2, 'C2 should be a sort header' ); - assert.equal( $table.find( '#C1' ).prop( 'headerIndex' ), + assert.equal( $table.find( '#C1' ).data( 'headerIndex' ), undefined, 'C1 should not be a sort header' ); @@ -1218,9 +1218,10 @@ '' ); $table.tablesorter(); - assert.equal( $table.find( 'tr:eq(1) th:eq(1)').prop('headerIndex'), + assert.equal( $table.find( 'tr:eq(1) th:eq(1)').data('headerIndex'), 2, - 'Incorrect index of sort header' ); + 'Incorrect index of sort header' + ); } );