jQuery: this: "$(this).next().next()" 有效,但 "$(this).next('.div')" 无效

jQuery: this: "$(this).next().next()" works, but "$(this).next('.div')" does Not

好的,我正在尝试让这组信息单独隐藏。

<img class="arrow" src="images/navigation/arrowright.png">
<H2>More Information</H2>
<div class="box">
    <h2>Bibendum Magna Lorem</h2>
    <p>Cras mattis consectetur purus sit amet fermentum.</p>
</div>

<img class="arrow" src="images/navigation/arrowright.png">
<H2>A Second Group of Information</H2>
<div class="box">
    <h2>Bibendum Magna Lorem</h2>
    <p>Cras mattis consectetur purus sit amet fermentum.</p>
</div>

当我输入这个时它起作用了:

$(".arrow").click(function() {
    $(this).next().next().slideToggle();
});

但我这样做的时候不是:

$(".arrow").click(function() {
    $(this).next('.box').slideToggle();
});

发生了什么导致第二个选项不起作用?我已经研究了好几天了,他妈的想不通!感谢您的意见!

问题

如果您查看 .next(selector)documentation,它不会 "find" 匹配选择器的下一个同级。相反,它只查看下一个兄弟元素,如果它与不是您想要的选择器匹配,则只 return 那个元素。

.next() 的文档是这样说的:

Description: Get the immediately following sibling of each element in the set of matched elements. If a selector is provided, it retrieves the next sibling only if it matches that selector.

因此,您可以看到 .next(".box") 将查看紧跟在 .arrow 元素之后的 h2 元素(即下一个同级元素),然后将其与 .box 选择器,因为它们不匹配,它将 return 一个空的 jQuery 对象。


使用 .nextAll() 的解决方案

如果你想要下一个匹配选择器的兄弟,你可以使用这个:

$(this).nextAll(".box").eq(0).slideToggle();

这会找到所有匹配选择器的兄弟,然后只提取第一个。


创建您自己的 .findNext() 方法

我经常想知道为什么 jQuery 没有我自己制作的方法:

// get the next sibling that matches the selector
// only processes the first item in the passed in jQuery object
// designed to return a jQuery object containing 0 or 1 DOM elements
jQuery.fn.findNext = function(selector) {
    return this.eq(0).nextAll(selector).eq(0);
}

然后,您只需使用:

$(this).findNext(".box").slideToggle();

选项:向 HTML 添加更多结构,使事情更简单、更灵活

仅供参考,解决此类问题的一种常见方法是在每组 DOM 元素周围放置一个包含 div 的元素,如下所示:

<div class="container">
    <img class="arrow" src="images/navigation/arrowright.png">
    <H2>More Information</H2>
    <div class="box">
            <h2>Bibendum Magna Lorem</h2>
            <p>Cras mattis consectetur purus sit amet fermentum.</p>
    </div>
</div>

<div class="container">
     <img class="arrow" src="images/navigation/arrowright.png">
     <H2>A Second Group of Information</H2>
     <div class="box">
            <h2>Bibendum Magna Lorem</h2>
            <p>Cras mattis consectetur purus sit amet fermentum.</p>
     </div>    
</div>

然后,您可以使用对元素的精确定位不太敏感的代码:

$(".arrow").click(function() {
    $(this).closest(".container").find(".box").slideToggle();
});

这会使用 .closest() 上升到包含和公共父级,然后使用 .find() 找到该组中的 .box 元素。