2013-04-21 3 views
12

У меня есть несколько DIV с содержимым, которое имеет атрибут weight-weight, который регулярно обновляется через AJAX.Повторная компоновка/сортировка DIV без повторной установки в DOM

Я сортирую их в цикле, где я перебираю новые значения, исходящие из ajax-запроса.

Поскольку вес данных может быть обновлен в любое время до любого значения, заказ может полностью измениться с момента обновления до обновления.

Моя логика сортировки кажется ошибочной (по меньшей мере;)), потому что она сравнивает каждый элемент с его следующим через .next(), поэтому вам нужно нажать «Сортировать по весу данных» макс. 4 раза для 4 элементов, пока они не будут отсортированы (см. Скрипку ниже).

Важно знать, что сортируемые DIV содержат внешние ресурсы, такие как изображения, видео и т. Д., Поэтому важно, чтобы они перемещались и не воссоздавались, потому что я думаю, что при повторном вставке в DOM оставшиеся ресурсы повторно загружаются, что неприемлемо для моего прецедента.

Как трудно descripte и, возможно, понять, вот моя скрипка:

http://jsfiddle.net/PdGTK/5/

Update

Хотя главная проблема решена, все еще существует проблема, когда F.E. Youtube-Videos включены, они перезагружаются каждый раз, когда DIVs переупорядочиваются, даже если видео не меняется в DOM. Это а) выглядит странно и б) прерывает видео-игру. Читайте больше о теме, перемещая фреймы в DOM всегда, кажется, заставляют их перезагружать свой контент - как это глупо?

Fiddle обновляется с фиксированным весом данных 1 для YT-видео, поэтому он всегда остается на вершине.

http://jsfiddle.net/PdGTK/10/

Идеи очень приветствуется !!

ответ

14

Вот первый способ, что пришло на ум:

$("#sortButton").on("click", function() { 
    var $wrapper = $('#wrapper'), 
     $articles = $wrapper.find('.article'); 
    [].sort.call($articles, function(a,b) { 
     return +$(a).attr('data-weight') - +$(b).attr('data-weight'); 
    }); 
    $articles.each(function(){ 
     $wrapper.append(this); 
    }); 
}); 

Кажется, работает: http://jsfiddle.net/PdGTK/6/

В основном то, что делает создает объект JQuery ($articles), который содержит все статьи. Затем он сортирует элементы в объекте jQuery в соответствии с их атрибутом data-weight. Затем он проходит через них в новом порядке и добавляет их в обертку - отмечая, что когда вы .append() элемент, который уже находится в DOM, он перемещается.

+0

В конце концов, почему бы вам не сделать '$ wrapper.append ($ articles)'? –

+0

@AlessandroVendruscolo - Потому что я не умный. (См. Также вступительное предложение моего ответа.) Но да, это должно сработать. – nnnnnn

+0

спасибо! Выглядит хорошо. Если я буду использовать предложение @AlessandroVendruscolo, разве это не помешало бы мне указать, что они должны быть перемещены, а не повторно вставлены? –

5

Это, как вы можете сортировать его:

var $wrapper = $('#wrapper'), 
    $art = $wrapper.children('.article'); 

$art.sort(function(a, b) { 
    return +$(a).data('weight') - +$(b).data('weight'); 
}) 
.each(function() { 
    $wrapper.append(this); 
}); 

http://jsfiddle.net/dfsq/PdGTK/8/

+0

ваша скрипка не работает для меня, но lorempixel отлично знать о. Благодаря! –

+0

Что это значит, что это не работает, разве это не сортировка статей по весу данных? – dfsq

+0

точно, на моей машине (OSX/safari) он не сортируется. –

1

мне нужно тоже изменить порядок элементов без повторной вставки в DOM. Вы можете сделать это, изменив свойство CSS.

Для внешнего контейнера набор CSS собственности:

display: flex; 
flex-direction: column; 

и для каждого набора элементов:

order: X; 

где Х растет в порядке возрастания.

+0

это хорошая идея, и для переустановки просто установите порядок нового –

Смежные вопросы