jQuery sortColumns插件:如何使用rowspan正确排序

Tha*_*ham 7 html javascript jquery

按照这个帖子jQuery表排序(github链接:https://github.com/padolsey/jQuery-Plugins/blob/master/sortElements/jquery.sortElements.js),我成功排序列,但它不能在rowspan的情况:例如,这样的情况

 Grape      3,096,671M
            1,642,721M
 Apple      2,602,750M
            3,122,020M
Run Code Online (Sandbox Code Playgroud)

当我点击第二列时,它会尝试排序

 Apple      2,602,750M
            1,642,721M
 Grape      3,096,671M
            3,122,020M
Run Code Online (Sandbox Code Playgroud)

(预期结果应该是它应该只在每个行间隔内排序

 Grape      1,642,721M
            3,096,671M
 Apple      2,602,750M
            3,122,020M
Run Code Online (Sandbox Code Playgroud)

要么

 Grape      3,096,671M
            1,642,721M
 Apple      3,122,020M
            2,602,750M
Run Code Online (Sandbox Code Playgroud)

)

所以你可以看到哪个不正确,请任何jQuery大师帮我解决这个问题.这是我的代码

var inverse = false;
function sortColumn(index){
    index = index + 1;
    var table = jQuery('#resultsTable');
    table.find('td').filter(function(){
        return jQuery(this).index() == index;
    }).sortElements(function(a, b){
        a = convertToNum($(a).text());
        b = convertToNum($(b).text());

        return (
            isNaN(a) || isNaN(b) ?
            a > b : +a > +b
            ) ?
        inverse ? -1 : 1 :
        inverse ? 1 : -1;
    },function(){
        return this.parentNode;
    });
    inverse = !inverse;
}
function convertToNum(str){
    if(isNaN(str)){
        var holder = "";
        for(i=0; i<str.length; i++){                                
            if(!isNaN(str.charAt(i))){
                holder += str.charAt(i);
            }
        }
        return holder;
    }else{
        return str;
    }
}
Run Code Online (Sandbox Code Playgroud)

题:

1.如何用rowspan对其进行排序.ROWSPAN的数量并不总是相同的.以上示例Grape和Apple的行距为2,但情况并非总是如此.

2.可以解释这个语法:

 return (
            isNaN(a) || isNaN(b) ?
            a > b : +a > +b
            ) ?
        inverse ? -1 : 1 :
        inverse ? 1 : -1;
Run Code Online (Sandbox Code Playgroud)

所以我可以看到,如果a或b不是数字,那么做字符串比较否则做数字比较,但我不明白

inverse ? -1 : 1 :
inverse ? 1 : -1;
Run Code Online (Sandbox Code Playgroud)

测试用例

<table id="resultsTable">
        <thead>
            <tr>
                <th>Fruit</th>
                <th onclick="sortColumn(1)">Quantity</th>
                <th onclick="sortColumn(2)">Rate</th>
            </tr>
        </thead>
        <tbody>
            <tr>
                <td rowspan="4">Grape</td>
                <td>15</td>
                <td>5</td>
            </tr>
            <tr>
                <td>4</td>
                <td>2</td>
            </tr>
            <tr>
                <td>88</td>
                <td>1</td>
            </tr>
            <tr>                    
                <td>11</td>
                <td>3</td>
            </tr>
            <tr>
                <td rowspan="3">Melon</td>
                <td>21</td>
                <td>2</td>
            </tr>
            <tr>
                <td>2</td>
                <td>0</td>
            </tr>
            <tr>
                <td>35</td>
                <td>1</td>
            </tr>
            <tr>
                <td rowspan="6">Melon</td>
                <td>24</td>
                <td>5</td>
            </tr>
            <tr>
                <td>66</td>
                <td>2</td>
            </tr>
            <tr>
                <td>100</td>
                <td>4</td>
            </tr>
            <tr>
                <td>21</td>
                <td>1</td>
            </tr>
            <tr>
                <td>65</td>
                <td>3</td>
            </tr>
            <tr>
                <td>2</td>
                <td>0</td>
            </tr>
        </tbody>
 <table>
Run Code Online (Sandbox Code Playgroud)

New*_*o.O 3

代码运行的条件:

  • td包含s with 的列rowspan必须全部位于表格的左侧
  • td这些列中的所有s 都必须有 a rowspan,即使它是 1
  • 要排序的行组是由这些列中最右边的列组成的(但可以轻松更改)

jsFiddle: http: //jsfiddle.net/5GrAC/77/

var inverse = false;

function sortColumn(index) {
    var trs = $('#resultsTable > tbody > tr'),
        nbRowspans = trs.first().children('[rowspan]').length,
        offset = trs.first().children('[rowspan]').last().offset().left;

    var tds = trs.children('[rowspan]').each(function() {
        $(this).data('row', $(this).parent().index());
        $(this).data('column', $(this).index());
        $(this).data('offset', $(this).offset().left)
    }).each(function() {
        if($(this).data('offset') != offset)
            return;

        var rowMin = $(this).data('row'),
            rowMax = rowMin + parseInt($(this).attr('rowspan'));

        trs.slice(rowMin, rowMax).children().filter(function() {
            return $(this).index() == index + $(this).parent().children('[rowspan]').length - nbRowspans;
        }).sortElements(function(a, b) {
            a = convertToNum($(a).text());
            b = convertToNum($(b).text());

            return (
                isNaN(a) || isNaN(b) ?
                a > b : +a > +b
                ) ?
            inverse ? -1 : 1 :
            inverse ? 1 : -1;
        }, function() {
            return this.parentNode;
        });
    });

    var trs = $('#resultsTable > tbody > tr');
    tds.each(function() {
        if($(this).parent().index() != $(this).data('row'))
            $(this).insertBefore(trs.eq($(this).data('row')).children().eq($(this).data('column')));
    });

    inverse = !inverse;
}
Run Code Online (Sandbox Code Playgroud)

快速解释:

  • 查找所有tds 与rowspan
  • 这些s的位置td被保存,包括左偏移
  • 这些tds 按其原始内容进行过滤,offset仅适用于最右边的
  • tr与每个保留相关的 std使用所需列进行排序
  • 如有必要,所有tdsrowspan最终都会移回原来的位置

关于问题2,我只会通过说来完成bartlaarhoven的回答,代码也可以写成如下:

return (
        (isNaN(a) || isNaN(b) ? a > b : +a > +b) ? 1 : -1
    ) * (inverse ? -1 : 1);
Run Code Online (Sandbox Code Playgroud)

您可以轻松阅读inverse用于反转结果的内容。

  • 我对代码进行了一些优化(有太多的搜索和过滤),它应该可以更好地处理大型表。 (2认同)