我参加聚会有点晚了,但我昨天和 Isotope 一起工作时遇到了同样的问题,最终以不同的方式解决了它。
假设我有一组过滤器按钮,很像 Systembolaget 的:
<div id="filters">
<button data-filter="*">Show all</button>
<button data-filter=".hidden">Archived</button>
<button data-filter="*:not(.hidden)">Current</button>
</div>
也许我只想在用户完成加载页面时显示“当前”过滤器。我为与我想要的过滤器匹配的 CSS 选择器设置了一个变量。我们稍后会使用这个变量。
var $grid;
var filterValue = "*:not(.hidden)";
接下来,我需要初始化我的内容。我已经准备好我的内容,所以我跳过了这一步,但如果你打算异步加载内容,你可以使用 JavaScript Promise。
这是我取自Google's Promise introduction article的一个例子:
var promise = new Promise(function(resolve, reject) {
var content = [];
// do a thing, possibly async, then…
if (content.length > 0) {
resolve(content);
}
else {
reject(Error("Nothing loaded"));
}
});
这是我用来设置同位素网格和事件监听器的函数:
function init() {
// Initialize isotope and the filter method we want to use
$grid = $('.grid').isotope({
itemSelector: '.grid-item',
filter: function() {
return filterValue ? $(this).is(filterValue) : true;
}
});
// Event listener for the filter buttons
$('#filters').on('click', 'button', function() {
filterValue = $(this).attr('data-filter');
$(this).addClass('active')
.siblings().removeClass('active');
// Refresh the isotope grid to display the filtered items
$grid.isotope();
});
}
一旦你定义了 Promise 应该做什么,你就可以初始化你的同位素网格。您需要将它嵌套在 then 方法中,以便它仅在 promise 成功解决后运行。这还允许您设置在内容加载步骤失败的情况下应该运行的任何后备。
promise.then(function(results) {
// Function defined in the last code snippet
return init();
}, function(err) {
// Error: "Nothing loaded"
console.log(err);
// If you have a banner hidden on the page, you can display it
$('.message').show();
});
如果您不需要使用承诺(如我的情况),那么您需要做的就是:
init();