如何使用 JQuery 在具有不同元素的列表中获取下一个同级匹配

问题描述

出于某种原因,我在使用 <li><div> 获取列表中的下一个匹配项时遇到问题。我只需要匹配在点击的 .infoBox 之后匹配的下一个 <li>

<ul>
  <li />
  <li />
  <li />
  <div class="infoBox" />
  <li />
  <li />
  <li />
  <div class="infoBox" />
  ...repeats this pattern a few more times

尝试 1

$('ul li').on('click',function() {
  $(this).nextAll('.infoBox').first();
});

有了这个,点击第三个 <li /> 不会选择 .infoBox

// e.g.
<li />
<li />
<li />
<div class="infoBox" />
// clicking on the first <li /> selects the last <li /> and .infoBox
// clicking on the second <li /> selects the .infoBox correctly
// clicking on the third <li /> does not select .infoBox at all

尝试 2

$('ul li').on('click',function() {
  $(this).next('.infoBox');
});

有了这个,只点击第三个 <li> 就会选择 .infoBox

// e.g.
<li />
<li />
<li />
<div class="infoBox" />
// clicking on the first <li /> does not select .infoBox
// clicking on the second <li /> does not select .infoBox
// clicking on the third <li /> selects .infoBox

尝试 3

$('ul li').on('click',function() {
  $(this).nextUntil('.infoBox').next().last();
});

有了这个,点击第三个 <li> 不会选择 .infoBox

// e.g.
<li />
<li />
<li />
<div class="infoBox" />
// clicking on the first <li /> selects .infoBox
// clicking on the second <li /> selects .infoBox
// clicking on the third <li /> does not select .infoBox

解决方法

更新:

实际上可以使用 jQuery 更快地做到这一点, 在选择器中使用 pseudo 类:.nextAll('.infobox:first')

$('li').on('click',function() {
  $(this).nextAll('.infobox:first').addClass('red');
});
.red {
  color: red;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<ul>
  <li>not infobox</li>
  <li>not infobox</li>
  <li class="infobox">infobox</li>
  <li>not infobox</li>
  <li>not infobox</li>
  <li>not infobox</li>
  <li class="infobox">infobox</li>
</ul>


您需要遍历 li 数组中剩余的项目。

一旦找到一个类,您就需要 break 退出循环,否则所有具有该类的下一个兄弟都会被选中。

$('li').each(function(i) {
  $(this).on('click',function() {
    for(let j = i; j < $('li').length; j++){
      if($('li').eq(j).hasClass('infobox')){
        $('li').eq(j).addClass('red');
        break;
      }
    }
  });
});
.red {
  color: red;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<ul>
  <li>not infobox</li>
  <li>not infobox</li>
  <li class="infobox">infobox</li>
  <li>not infobox</li>
  <li>not infobox</li>
  <li>not infobox</li>
  <li class="infobox">infobox</li>
</ul>