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

求助:Owl-Carousel内Bootstrap Accordion图标异常如何解决?

解决Owl-Carousel内Bootstrap Accordion图标状态不匹配问题

问题现象

将Bootstrap Accordion嵌入Owl-Carousel轮播组件后,切换轮播项再返回时,Accordion的展开/折叠图标无法正确对应实际状态——比如面板明明是展开的,但图标显示为折叠状态,反之亦然。

问题原因

Owl Carousel在切换轮播时,会对非当前活跃的轮播项进行DOM隐藏或重新渲染操作,导致Bootstrap Accordion依赖的collapsed类、aria-expanded属性以及面板的show类,在轮播切换后无法保持正确的同步关系,最终引发图标显示异常。

解决方案

通过监听Owl Carousel的轮播切换完成事件,在每次切换后主动校验并同步当前活跃轮播项内Accordion的状态,确保图标与实际展开/折叠状态一致。

具体实现步骤

  1. 在轮播切换完成的changed.owl.carousel事件处理函数中,定位当前显示的轮播项。
  2. 遍历该轮播项内的所有Accordion按钮,根据对应面板的展开状态,手动更新按钮的collapsed类和aria-expanded属性。

修改后的代码

JavaScript部分

var bigimage = $("#big");
var thumbs = $("#thumbs");
var syncedSecondary = true;

bigimage
  .owlCarousel({
    items: 1,
    nav: false,
    autoplay: false,
    dots: false,
    loop: true,
    navText: [
      '<i class="fa fa-arrow-left" aria-hidden="true"></i>',
      '<i class="fa fa-arrow-right" aria-hidden="true"></i>',
    ],
  })
  .on("changed.owl.carousel", syncPosition);

thumbs
  .on("initialized.owl.carousel", function () {
    thumbs.find(".owl-item").eq(0).addClass("current");
  })
  .owlCarousel({
    items: 6,
    dots: false,
    nav: false,
    mouseDrag: false,
    navText: [
      '<i class="fa fa-arrow-left" aria-hidden="true"></i>',
      '<i class="fa fa-arrow-right" aria-hidden="true"></i>',
    ],
    responsive: {
      0: {
        items: 1,
        nav: true,
      },
      600: {
        items: 3,
      },
      1000: {
        items: 6,
      },
    },
  })
  .on("changed.owl.carousel", syncPosition2);

function syncPosition(el) {
  var count = el.item.count - 1;
  var current = Math.round(el.item.index - el.item.count / 2 - 0.5);

  if (current < 0) {
    current = count;
  }
  if (current > count) {
    current = 0;
  }
  thumbs
    .find(".owl-item")
    .removeClass("current")
    .eq(current)
    .addClass("current");
  var onscreen = thumbs.find(".owl-item.active").length - 1;
  var start = thumbs.find(".owl-item.active").first().index();
  var end = thumbs.find(".owl-item.active").last().index();

  if (current > end) {
    thumbs.data("owl.carousel").to(current, 100, true);
  }
  if (current < start) {
    thumbs.data("owl.carousel").to(current - onscreen, 100, true);
  }

  // 新增:同步当前轮播项内的Accordion状态
  var activeSlide = bigimage.find(".owl-item.active .accordion");
  if (activeSlide.length > 0) {
    activeSlide.find(".accordion-button").each(function() {
      var targetId = $(this).data("bs-target");
      var isExpanded = $(targetId).hasClass("show");
      $(this).toggleClass("collapsed", !isExpanded);
      $(this).attr("aria-expanded", isExpanded);
    });
  }
}

function syncPosition2(el) {
  if (syncedSecondary) {
    var number = el.item.index;
    bigimage.data("owl.carousel").to(number, 100, true);
  }
}

thumbs.on("click", ".owl-item", function (e) {
  e.preventDefault();
  var number = $(this).index();
  bigimage.data("owl.carousel").to(number, 300, true);
});

HTML部分(无需修改,保留原结构即可)

<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/bootstrap@5.2.0/dist/js/bootstrap.bundle.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/OwlCarousel2/2.3.4/owl.carousel.min.js"></script>

<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.2.0/dist/css/bootstrap.min.css" rel="stylesheet"/>
<link href="https://cdnjs.cloudflare.com/ajax/libs/OwlCarousel2/2.3.4/assets/owl.carousel.css" rel="stylesheet"/>

<div>
  <section class="our-blogs-wrapper">
    <div class="outer">
      <div id="big" class="ourBlogsSlider owl-carousel owl-theme">
        <div class="item">
          <div class="container-fluid">
            <div class="row row-cols-1 row-cols-1 g-5">
              <div class="col">
                <div class="card h-100 shadow-none">
                  <div class="card-body">
                    <div class="accordion" id="accordionExample">
                      <div class="accordion-item">
                        <h2 class="accordion-header" id="headingOne">
                          <button class="accordion-button" type="button"
                            data-bs-toggle="collapse" data-bs-target="#collapseOne"
                            aria-expanded="true" aria-controls="collapseOne">
                            Accordion Item #1
                          </button>
                        </h2>
                        <div id="collapseOne" class="accordion-collapse collapse show"
                          aria-labelledby="headingOne" data-bs-parent="#accordionExample">
                          <div class="accordion-body">
                            <strong>This is the first item's accordion body.</strong> It
                            is
                            shown by default, until the collapse plugin adds the
                            appropriate
                            classes that we use to style each element. These classes
                            control
                            the overall appearance, as well as the showing and hiding
                            via
                            CSS transitions. You can modify any of this with custom CSS
                            or
                            overriding our default variables. It's also worth noting
                            that
                            just about any HTML can go within the
                            <code>.accordion-body</code>, though the transition does
                            limit
                            overflow.
                          </div>
                        </div>
                      </div>
                      <div class="accordion-item">
                        <h2 class="accordion-header" id="headingTwo">
                          <button class="accordion-button collapsed" type="button"
                            data-bs-toggle="collapse" data-bs-target="#collapseTwo"
                            aria-expanded="false" aria-controls="collapseTwo">
                            Accordion Item #2
                          </button>
                        </h2>
                        <div id="collapseTwo" class="accordion-collapse collapse"
                          aria-labelledby="headingTwo" data-bs-parent="#accordionExample">
                          <div class="accordion-body">
                            <strong>This is the second item's accordion body.</strong>
                            It is
                            hidden by default, until the collapse plugin adds the
                            appropriate classes that we use to style each element. These
                            classes control the overall appearance, as well as the
                            showing
                            and hiding via CSS transitions. You can modify any of this
                            with
                            custom CSS or overriding our default variables. It's also
                            worth
                            noting that just about any HTML can go within the
                            <code>.accordion-body</code>, though the transition does
                            limit
                            overflow.
                          </div>
                        </div>
                      </div>
                      <div class="accordion-item">
                        <h2 class="accordion-header" id="headingThree">
                          <button class="accordion-button collapsed" type="button"
                            data-bs-toggle="collapse" data-bs-target="#collapseThree"
                            aria-expanded="false" aria-controls="collapseThree">
                            Accordion Item #3
                          </button>
                        </h2>
                        <div id="collapseThree" class="accordion-collapse collapse"
                          aria-labelledby="headingThree"
                          data-bs-parent="#accordionExample">
                          <div class="accordion-body">
                            <strong>This is the third item's accordion body.</strong> It
                            is
                            hidden by default, until the collapse plugin adds the
                            appropriate classes that we use to style each element. These
                            classes control the overall appearance, as well as the
                            showing
                            and hiding via CSS transitions. You can modify any of this
                            with
                            custom CSS or overriding our default variables. It's also
                            worth
                            noting that just about any HTML can go within the
                            <code>.accordion-body</code>, though the transition does
                            limit
                            overflow.
                          </div>
                        </div>
                      </div>
                    </div>
                  </div>
                </div>
              </div>
            </div>
          </div>
        </div>
        <div class="item">
        </div>
        <div class="item">
        </div>
        <div class="item">
        </div>
        <div class="item">
        </div>
        <div class="item">
        </div>
      </div>
    </div>
  </section>
</div>

说明

新增的代码逻辑会在每次轮播切换完成后,自动检查当前显示的轮播项中的所有Accordion按钮,根据对应面板是否有show类(即是否展开),来更新按钮的collapsed类和aria-expanded属性,确保图标状态与实际展开/折叠状态完全匹配。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.21 02:45:49