You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

CSS :not(:first-of-type)选择器作用于div不生效问题排查

问题成因

CSS原生的:first-of-type选择器匹配规则是选中同父元素下、同标签类型的第一个子元素,该类选择器(包括:last-of-type、:nth-of-type系列)仅按标签名做匹配,完全不识别class、id等自定义属性筛选条件,这是逻辑失效的核心原因。

查看你的DOM结构,.accordion-container下的直接子元素全部是div标签,排列顺序为:

  1. 第1个div:.accordion-title(Standard套餐标题)
  2. 第2个div:.accordion-content(第一个内容区)
  3. 第3个div:.accordion-title(Pro套餐标题)
  4. 第4个div:.accordion-content(第二个内容区)
  5. 第5个div:.accordion-title(Elite套餐标题)
  6. 第6个div:.accordion-content(第三个内容区)

你写的$(".accordion-content:not(:first-of-type)")逻辑,实际执行时会先找所有带.accordion-content类的div,再排除其中「父容器下第一个div」的元素——但所有.accordion-content对应的div分别是父容器下的第2、4、6个子元素,没有一个符合“同层级第一个div”的条件,因此该选择器选不到任何元素,隐藏逻辑完全不生效。

你之前测试把.accordion-content的标签换成p、h5就能正常运行,本质是换标签后,第一个.accordion-content成了父容器下第一个该标签类型的元素,剩余同标签的内容区刚好被:not(:first-of-type)命中,属于巧合匹配,并非原有逻辑正确。

顺带一提,你代码里$(".js-accordion-title:first-of-type")能正常给第一个标题加open类,只是因为第一个.accordion-title刚好是父容器下的第一个div,碰巧符合选择器规则,同样存在标签类型依赖的隐患。

可行解决方案

方案1:用jQuery集合过滤器(改动最小,零侵入)

jQuery自带的:first过滤器、.first()方法是针对已匹配到的jQuery元素集合取第一个元素,不受标签类型限制,完全匹配你的需求,只需要修改两行初始化代码即可,不需要调整HTML和CSS:

$(function() {
  // 选中所有内容区,排除集合内第一个,全部隐藏
  $(".accordion-content").not(":first").css("display", "none");
  // 给第一个标题添加open类
  $(".js-accordion-title").first().addClass("open");

  $(".js-accordion-title").click(function() {
    $(".open").not(this).removeClass("open").next().slideUp(300);
    $(this).toggleClass("open").next().slideToggle(300);
  });
});

方案2:默认状态写在CSS里(体验最好,无加载闪烁)

把默认展开/隐藏的逻辑直接写在CSS里,HTML提前给默认展开的项加状态类,既可以避免选择器匹配问题,还能解决JS初始化延迟导致的页面加载瞬间所有手风琴全展开的闪烁问题:

  1. 首先修改HTML,给默认展开的项预置状态类:
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="accordion" class="accordion-container">
  <!-- 给第一个标题预置open类 -->
  <div class="accordion-title js-accordion-title open">
    <h2 class="price-plan-name">Standard</h2>
    <h3 class="starting-price">Starting at
      <span class="price-number">$1,650</span></h3>
  </div>
  <!-- 给第一个展示的内容区预置active类 -->
  <div class="accordion-content is-active">
    <p>Accordion Content1</p>
  </div>
  <div class="accordion-title js-accordion-title">
    <h2>Pro</h2>
    <h3 class="accordion-subtitle">Starting at
      <span class="price-number">$2,950</span></h3>
  </div>
  <div class="accordion-content">
    Accordion Content2
  </div>
  <div class="accordion-title js-accordion-title">
    <h2>Elite</h2>
    <h3 class="accordion-subtitle">Starting at
      <span class="price-number">$3,950</span></h3>
  </div>
  <div class="accordion-content">
    Accordion Content3
  </div>
</div>
  1. 补充CSS默认状态规则:
.accordion-content {
  padding-left: 2.3125em;
  display: none; /* 所有内容区默认隐藏 */
}
.accordion-content.is-active {
  display: block; /* 激活状态的内容区展示 */
}
/* 其余原有CSS保持不变 */
  1. 简化JS逻辑,去掉初始化操作:
$(function() {
  $(".js-accordion-title").click(function() {
    // 重置其他展开项的状态
    $(".open").not(this).removeClass("open").next().removeClass("is-active").slideUp(300);
    // 切换当前项状态
    $(this).toggleClass("open").next().toggleClass("is-active").slideToggle(300);
  });
});

该方案维护性更强,后续新增手风琴项不需要调整选择器逻辑,首屏加载体验更好,是生产环境推荐的写法。


内容的提问来源于stack exchange,提问作者Versa

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.27 18:45:40