2015-07-04 51 views
2

我有一個todo列表。每行都有一個星形圖標,您可以點擊,就像gmail一樣。這裏的區別是,如果你點擊一個星星,它應該排序到頂部(較高的優先級),但也可以通過升序阿爾法在星號組內重新排序。未星標項目排序如下,也按升序排列。除了alpha排序,一切都按預期工作。下面是我正在做的那個排序功能。我已經驗證一切工作如下除了的//由阿爾法位的排序數組...在兩個組中使用jQuery按字母順序排序

排序失敗:

function sortTasks(currList) { 
    var starredTasks = []; 
    var unstarredTasks = []; 
    //create arrays 
    $('li.task').each(function(){ 
     if ($(this).children('img.star').attr('src') == "images/star_checked.gif") { 
      starredTasks.push($(this)); 
     } else { 
      unstarredTasks.push($(this)); 
     } 
    }); 
    //sort the arrays by alpha 
    starredTasks.sort(function(a,b){ ($(a).children('p.task-name').text().toUpperCase() > $(b).children('p.task-name').text().toUpperCase()) ? 1 : -1;}); 
    unstarredTasks.sort(function(a,b){ ($(a).children('p.task-name').text().toUpperCase() > $(b).children('p.task-name').text().toUpperCase()) ? 1 : -1;}); 
    //draw rows starred first, unstarred second 
    $(currList).empty(); 
    for (i=0; i < starredTasks.length; i++) { 
     $(currList).append(starredTasks[i]); 
    } 
    for (i=0; i < unstarredTasks.length; i++) { 
     $(currList).append(unstarredTasks[i]); 
    } 
} 

此數組已被填充與任務行按照它們最初繪製的順序。數據呈現良好,但基本保持相同的順序。

例任務行:

<div id="task-container" class="container"> 
    <form name="enter-task" method="post" action=""> 
     <input id="new-task" name="new-task" type="text" autofocus> 
    </form> 
    <h2 id="today">today</h2> 
     <ul id="today-list"> 
      <li id="457" class="task"> 
       <img class="star" src="images/star_checked.gif"> 
       <p class="task-name" contenteditable>buy milk</p> 
       <p class="task-date"> - Wednesday</p> 
      </li> 
     </ul> 
    <h2 id="tomorrow">tomorrow</h2> 
     <ul id="tomorrow-list"> 
     </ul> 
    <h2 id="future">future</h2> 
     <ul id="future-list"> 
     </ul> 
    <h2 id="whenever">whenever</h2> 
     <ul id="whenever-list"> 
     </ul> 
</div> 

的starredTasks陣列中的每一項是一個完整的任務行。我假設$(a)$(li)的水平相同?

和這裏的觸發排序功能:

$('body').on('click', 'img.star', function(){ 
    var thisList = '#' + $(this).parent('li').parent('ul').attr('id'); 
    if ($(this).attr('src') == 'images/star_checked.gif') { 
     $(this).attr('src', 'images/star_unchecked.gif'); 
    } else { 
     $(this).attr('src', 'images/star_checked.gif'); 
    } 
    sortTasks(thisList);   
}); 

而且,我懷疑這是值得一提,但數據存儲在MySQL的,並通過PHP預先填充。

我不知道的方式來使用.sort()直接在$('li')不拆分爲獨立數組...

任何人看到我的穿幫?

回答

2

我沒有看到你在哪裏添加排序列表回到DOM。如果你不是,那就是問題所在。排序元素數組根本不會更新DOM。

此外,您的排序非常昂貴。最好將具有與實際值配對的元素的對象數組進行排序。

最後,您似乎在頁面上多次使用相同的ID。這是錯誤的。它可能適用於jQuery的.children(selector)過濾器,但它仍然是錯誤的。你需要改變它。


在這裏,我映射包含一個text屬性保持排序的文本和保持元件的task屬性的對象的陣列。

我將p#task-name更改爲p.task-name,因此您應該將其更改爲class="task-name"上的元素。

然後我使用.localeCompare()進行排序,它返回一個數字值。

最後,.forEach()循環將元素附加到DOM。

var data = starredTasks.map(function(t) { 
    return { task: t, 
       text: $(t).children('p.task-name').text().toUpperCase() 
      }; 
}).sort(function(obj_a, obj_b) { 
    obj_a.text.localeCompare(obj_b.text); 

}).forEach(function(obj) { 
    original_container.append(obj.task); 
}); 

此處假定starredTasks是一個實際的數組。如果它是一個jQuery對象,那麼做starredTasks.toArray().map(func...

original_container表示一個jQuery對象,它是task元素的直接父級。

+0

感謝您的迴應!我正在做一個'.append()'。我沒有發佈所有代碼,以便於閱讀。我證實了其他一切正在發揮作用,並將其縮小到我的排序邏輯。同名的多個ID肯定是個問題。我會把它改成一堂課。好地方!我會試一試你的方法。 – 5PalmTechnique

+0

我們確實需要一個完全重現問題的最小示例。否則,我們只是在浪費時間來猜測你的問題。另外,請報告您可能具有的任何控制檯錯誤。 –

+1

已更新以顯示功能。我真的只是在分類邏輯方面遇到問題,而不想分散WIP位。這是我的第一篇文章,所以我還沒有得到禮節。謝謝你的幫助。 ;)因此,我更新了sortTasks()函數以使用您的邏輯,並且像我的原始函數一樣,它按星號正確排序任務,但alpha仍然不起作用......我不知道我錯過了什麼。沒有控制檯錯誤。 – 5PalmTechnique