我有一些 IDS,我想用它们来填充/生成一些 jQuery 对象。我在 ajax 请求中使用这些 IDS。 填充 jQuery 对象后,我想对它们进行排序。
必须在IE11中工作。
我的问题是: 目前我不知道最佳实践是什么样的,等待所有 ajax 请求以及所有 jQuery 对象被填充。
- 我必须等到所有ajax请求都完成(所以 始终,独立于响应代码(例如 .done 和 .fail))
- 我必须等到所有 jQuery 对象填充有 ajax 请求的结果
问题结论:在填充项目之前调用排序函数。
我尝试将整个代码分解为一个简单的示例,也许有人可以在这里提供帮助:
function sortEntries(a, b) {
var aa = ($(a).data('name') || '').toLowerCase(),
bb = ($(b).data('name') || '').toLowerCase();
return aa < bb ? -1 : aa > bb ? 1 : 0;
}
function getEntryInfo(infoObj, callback) {
function getLabelByResult(result) {
var name = '';
switch (result) { // For this demo, we don't use the response data.
case 'page-header':
name = 'Hello World 1';
break;
case 'thumbnails':
name = 'It works!';
break;
case 'nav':
name = 'Great!';
break;
case 'btn-groups':
name = 'BTN GROUP';
break;
default:
name = 'NOT SET!'
}
return name;
}
return $.ajax({
method: 'GET',
url: infoObj.URI,
cache: false
}).done(function(data) {
if ($.isFunction(callback)) {
callback(true, {
name: getLabelByResult(infoObj.element)
});
}
}).fail(function() {
if ($.isFunction(callback)) {
callback(false, {
name: getLabelByResult(infoObj.element)
});
}
});
}
function setInfoForEntry(item$, config) {
return getEntryInfo(config, function(isOk, responseObjInfo) {
item$.attr('data-name', responseObjInfo.name || '').text(responseObjInfo.name || '');
});
}
function generateItems() {
var parentItem$ = $('body').append($('<ul/>').addClass('allItems').hide()),
ids = ['page-header', 'thumbnails', 'nav', 'btn-groups'], // for testing purposes of course
requests = [],
extractedItems$;
$.each(ids, function(ignorel, el) {
var newItem$ = $('<li/>').addClass('idItem').on('click', function(e) {
alert($(e.currentTarget).data('name'));
});
parentItem$.append(newItem$);
requests.push(setInfoForEntry(newItem$, {
URI: 'https://getbootstrap.com/docs/3.3/components/#/' + el,
element: el
}));
});
// HERE I HAVE TO ENSURE THAT:
// -ALL AJAX REQUESTS ARE DONE
// -ALL jQuery Elements are filled
extractedItems$ = parentItem$.find('.idItem');
extractedItems$.sort(sortEntries);
extractedItems$.detach().appendTo(parentItem$);
parentItem$.show();
}
$(document).ready(function() {
generateItems();
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<body></body>
最佳答案
为了等待多个 Promise,jQuery 有 $.when()
实用函数。另请参阅this thread和 this thread (有很多帖子讨论了这个问题,看看吧)。
我还稍微简化了您的代码,我认为这样更容易阅读:
function by(func) {
return function (a, b) {
var aa = func(a), bb = func(b);
return aa < bb ? -1 : aa > bb ? 1 : 0;
};
}
$(function () {
var things = {
'page-header': 'Hello World 1',
'thumbnails': 'It works!',
'nav': 'Great!',
'btn-groups': 'BTN GROUP'
}, requests;
requests = $.map(Object.keys(things), function (key) {
return $.get('https://getbootstrap.com/docs/3.3/components/#/' + key)
.then(function (data) {
return $('<li class="idItem">', {text: things[key] || 'NOT SET!'})[0];
});
});
$.when.apply($, requests).done(function () {
// each argument here is a single <li> element
var items = $(arguments).sort(by(function (el) {
return ($(el).text() || '').toLowerCase();
}));
$('<ul class="allItems">').appendTo('body').append(items);
}).fail(function (jqXhr, status, error) {
// show error
});
});
关于javascript - 填充/生成多个 jQuery 元素并在 ajax 请求后对它们进行排序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48973465/