如何在同一页面添加多个带下拉筛选的jQuery Isotope瀑布流布局
解决多Isotope瀑布流筛选冲突问题
我参考示例实现多Isotope瀑布流布局,目标是让带下拉筛选的画廊独立工作、筛选操作互不冲突。初始化了.grid和.grid2两个布局后,筛选功能出现冲突,官方文档未覆盖该场景,求修改JavaScript代码。
相关HTML代码
<div class="filters"> <div class="ui-group"> <h3>Color</h3> <select class="filter-select" value-group="color"> <option value="">any</option> <option value=".red">red</option> <option value=".blue">blue</option> <option value=".yellow">yellow</option> </select> </div> </div> <div class="grid"> <div class="color-shape red"></div> <div class="color-shape blue"></div> <div class="color-shape yellow"></div> </div> <div class="filters"> <div class="ui-group"> <h3>Size</h3> <select class="filter-select" value-group="size"> <option value="">any</option> <option value=".small">small</option> <option value=".wide">wide</option> <option value=".big">big</option> <option value=".tall">tall</option> </select> </div> <div> <div class="grid2"> <div class="color-shape2 small"></div> <div class="color-shape2 big"></div> <div class="color-shape2 small"></div> </div>
原示例JavaScript代码
// external js: isotope.pkgd.js // init Isotope var $grid = $('.grid').isotope({ itemSelector: '.color-shape' }); // store filter for each group var filters = {}; $('.filters').on( 'change', function( event ) { var $select = $( event.target ); // get group key var filterGroup = $select.attr('value-group'); // set filter for group filters[ filterGroup ] = event.target.value; // combine filters var filterValue = concatValues( filters ); // set filter for Isotope $grid.isotope({ filter: filterValue }); }); // flatten object by concatting values function concatValues( obj ) { var value = ''; for ( var prop in obj ) { value += obj[ prop ]; } return value; }
我的尝试代码
// external js: isotope.pkgd.js // init Isotope var $grid = $('.grid').isotope({ itemSelector: '.color-shape' }); var $grid2 = $('.grid2').isotope({ itemSelector: '.color-shape2' }); // store filter for each group var filters = {}; $('.filters').on( 'change', function( event ) { var $select = $( event.target ); // get group key var filterGroup = $select.attr('value-group'); // set filter for group filters[ filterGroup ] = event.target.value; // combine filters var filterValue = concatValues( filters ); // set filter for Isotope $grid.isotope({ filter: filterValue }); }); // flatten object by concatting values function concatValues( obj ) { var value = ''; for ( var prop in obj ) { value += obj[ prop ]; } return value; }
解决思路及修改后的代码
问题核心是共用了同一个全局filters对象,且筛选事件未关联对应目标网格,导致操作互相干扰。需要给每个筛选组和网格建立绑定关系,各自维护独立的筛选状态。
修改步骤
- 给每个
.filters容器添加data-target-grid属性,指定它控制的网格选择器 - 为每个网格维护独立的筛选对象,避免全局污染
- 在筛选事件中,仅更新对应网格的筛选状态
修改后的HTML(关键调整)
<div class="filters" data-target-grid=".grid"> <!-- 第一个筛选组内容 --> </div> <!-- ... --> <div class="filters" data-target-grid=".grid2"> <!-- 第二个筛选组内容 --> </div>
修改后的JavaScript代码
// external js: isotope.pkgd.js // 初始化所有Isotope网格,统一管理 var grids = { '.grid': $('.grid').isotope({ itemSelector: '.color-shape' }), '.grid2': $('.grid2').isotope({ itemSelector: '.color-shape2' }) }; // 为每个网格分配独立的筛选状态 var gridFilters = { '.grid': {}, '.grid2': {} }; // 监听筛选器变更事件 $('.filters').on('change', function(event) { var $select = $(event.target); // 获取当前筛选器对应的目标网格 var targetGridSelector = $(this).data('target-grid'); var $targetGrid = grids[targetGridSelector]; var targetFilters = gridFilters[targetGridSelector]; // 更新当前筛选组的条件 var filterGroup = $select.attr('value-group'); targetFilters[filterGroup] = event.target.value; // 组合筛选条件并应用到目标网格 var filterValue = concatValues(targetFilters); $targetGrid.isotope({ filter: filterValue }); }); // 合并筛选条件的工具函数 function concatValues(obj) { var value = ''; for (var prop in obj) { value += obj[prop]; } return value; }
说明
- 通过
data-target-grid建立筛选器与网格的一一对应关系,确保操作不会串位 - 每个网格拥有独立的筛选状态对象,互不干扰
- 事件处理仅针对当前筛选器绑定的网格,避免全局状态污染
内容的提问来源于stack exchange,提问作者McHunkerson
相关产品推荐
相关产品推荐

