17

I am trying to build a page using both bootstrap and a Owl carousel, Owl carousel fit the purpose of the site rather that bootstraps version. So I got a tab structure where I want to put a carousel on each page, however all my attempts have failed. Here is my code

<div role="tabpanel">

<!-- Nav tabs -->
<ul class="nav nav-tabs" role="tablist">
 <li role="presentation" class="active"><a href="#home" aria-controls="home" role="tab" data-toggle="tab">Home</a></li>
 <li role="presentation"><a href="#profile" aria-controls="profile" role="tab" data-toggle="tab">Profile</a></li>
 <li role="presentation"><a href="#messages" aria-controls="messages" role="tab" data-toggle="tab">Messages</a></li>
 <li role="presentation"><a href="#settings" aria-controls="settings" role="tab" data-toggle="tab">Settings</a></li>
</ul>

<!-- Tab panes -->
<div class="tab-content">
 <div role="tabpanel" class="tab-pane active" id="home">
  <div class="owl-carousel" id="owl1">
   <div> content</div>
   <div> content</div>
  </div>
 </div>
 <div role="tabpanel" class="tab-pane" id="profile">
  <div class="owl-carousel" id="owl2">
   <div> content</div>
   <div> content</div>
  </div>
 <div role="tabpanel" class="tab-pane" id="messages">
  <div class="owl-carousel" id="owl3">
   <div> content</div>
   <div> content</div>
  </div>
 </div>
<div role="tabpanel" class="tab-pane" id="settings">
  <div class="owl-carousel" id="owl4">
   <div> content</div>
   <div> content</div>
  </div>
 </div>
</div>
</div>

Here is my javascript

$(document).ready(function () {
    $('#owl1').owlCarousel({
        loop: true,
        margin: 10,
        responsiveClass: true,
        responsive: {
            0: {
               items: 1,
                nav: true
            },
            600: {
                items: 1,
                nav: false
            },
            1000: {
                items: 1,
                nav: true,
                loop: false
            }
        }
    });
    $('#owl2').owlCarousel({
        loop: true,
        margin: 10,
        responsiveclass: true,
        responsive: {
            0: {
                items: 1,
                nav: true
            },
            600: {
                items: 1,
                nav: false
            },
            1000: {
                items: 1,
                nav: true,
                loop: false
            }
        }
    });
    $('#owl3').owlCarousel({
        loop: true,
        margin: 10,
        responsiveclass: true,
        responsive: {
            0: {
                items: 1,
                nav: true
            },
            600: {
                items: 1,
                nav: false
            },
            1000: {
                items: 1,
                nav: true,
                loop: false
            }
        }
    });
    $('#owl4').owlCarousel({
        loop: true,
        margin: 10,
        responsiveclass: true,
        responsive: {
            0: {
                items: 1,
                nav: true
            },
            600: {
                items: 1,
                nav: false
            },
            1000: {
                items: 1,
                nav: true,
                loop: false
            }
        }
    });

//});

http://www.owlcarousel.owlgraphic.com/docs/api-events.html

jsg
  • 1,224
  • 7
  • 22
  • 44
  • 1
    Is this your literal HTML or you have simplified it? Because it misses all of the Owl carousel classes without which it won't work. –  Feb 05 '15 at 15:48
  • yep thats about it starting from the very start – jsg Feb 05 '15 at 16:00
  • what version of bootstrap are you using, can you put that on jsfidle please – bmscomp May 20 '15 at 10:36
  • Ive had some trouble trying to put this on jsfiddle but it is the latest version of bootstrap and owl carousel – jsg May 20 '15 at 11:09
  • Can you use this jsfiddle as a starting point (http://jsfiddle.net/67zq4f4o/)? What exactly isn't working for you? – DigitalDan May 21 '15 at 15:33
  • Well as you can see the on the example, the first tab is ok but on the second and third tabs are showing all the carousels all at once – jsg May 22 '15 at 10:00
  • 1
    Owl Carousel requires the ability to see the full width of an element to properly space it out on creation when using the auto width feature. Hidden elements present a problem when using the auto width feature as it is unable to detect the actual width. Since version 2.0 is still in beta, not all of the features will be in full working order, but I would suggest trying to call the resize/refresh event when the bootstrap show.bs.tab event is fired, or shown.bs.tab event. – Pynt May 26 '15 at 12:49

6 Answers6

22

First, I noticed an error in your html. You are missing a closing </div> tag for your second tab-pane. That's throwing off some of the structure of your markup.

After researching and playing around with this, it seems that this is a known issue. It stems from the fact that Bootstraps tabs are hidden initially. When you try to initialize an OwlCarousel within a hidden element, things go badly because hidden elements have no width, so Owl does not know how much space it has to work with.

My solution is to wait until a tab is shown to initialize the carousel, then destroy the carousel each time the tab is hidden. Here's my JavaScript:

$(document).ready(function () {
  initialize_owl($('#owl1'));

  let tabs = [
    { target: '#home', owl: '#owl1' },
    { target: '#profile', owl: '#owl2' },
    { target: '#messages', owl: '#owl3' },
    { target: '#settings', owl: '#owl4' },
  ];

  // Setup 'bs.tab' event listeners for each tab
  tabs.forEach((tab) => {
    $(`a[href="${ tab.target }"]`)
      .on('shown.bs.tab', () => initialize_owl($(tab.owl)))
      .on('hide.bs.tab', () => destroy_owl($(tab.owl)));
  }); 
});

function initialize_owl(el) {
  el.owlCarousel({
    loop: true,
    margin: 10,
    responsiveClass: true,
    responsive: {
      0: {
        items: 1,
        nav: true
      },
      600: {
        items: 1,
        nav: false
      },
      1000: {
        items: 1,
        nav: true,
        loop: false
      }
    }
  });
}

function destroy_owl(el) {
  el.data('owlCarousel').destroy();
}

And here's a working jsFiddle.

Vince
  • 3,207
  • 1
  • 17
  • 28
  • 1
    If you want to keep the carousel state you can even remove the hide.bs.tab handlers. https://jsfiddle.net/gsmiro/atk4j78r/ – Grasshopper May 26 '15 at 12:36
5

No more JavaScript is needed than the owl carousel option.

Just replace the following lines in the bootstrap.css file and all should work well.

.tab-content > .tab-pane {
     visibility: hidden;
     height: 0px;
     overflow:hidden;
}
.tab-content > .active {
     visibility: visible;
     height: auto;
     overflow: visible;
}
TylerH
  • 20,799
  • 66
  • 75
  • 101
user6038744
  • 59
  • 1
  • 1
  • Thanks for the heads up, I was trying to get the owl-carousel to worki inside a AJAX Magnific Popup. I removed the mfp-hide class and replaced it with a class that contains your first three rules, then I merely use jQuery to remove the class before I call the owl-carousel method and its works :) – Paul 501 Jun 24 '16 at 12:34
3

This is the best solution:

https://www.youtube.com/watch?v=tKrt9ev4S24

.tab-content > .tab-pane{
    display: block;
    height: 0;
}

.tab-content > .active{
    height: auto;
}
jupa8712
  • 81
  • 7
  • Just a quick update for anyone using this in 2021. It works. I'm using Bootstrap 4.5 and Owl Carousel 2.3.4. This solution is better for me since it uses CSS only rather than JS as described in the answer in this post. – Ivan Aldwin A. Cristobal Jul 11 '21 at 13:24
  • thats works for me for version 2.3.4. Thanks – vrajesh Mar 02 '22 at 09:39
1

Dear friend you can put the following piece of code instead of "owl.carousel.css" until the problem is resolved.

/* 
 *  Core Owl Carousel CSS File
 *  v1.3.3
 */

/* clearfix */
.owl-carousel .owl-wrapper:after {
    content: ".";
    display: block;
    clear: both;
    visibility: hidden;
    line-height: 0;
    height: 0;
}
/* display none until init */
.owl-carousel{
    display: none;
    position: relative;
    width: 100%;
    -ms-touch-action: pan-y;
}
.owl-carousel .owl-wrapper{
    display: none;
    position: relative;
    -webkit-transform: translate3d(0px, 0px, 0px);
    float: left;
}
.owl-carousel .owl-wrapper-outer{
    float: left;
    overflow: hidden;
    position: relative;
    width: 200%;
}
.owl-carousel .owl-wrapper-outer.autoHeight{
    -webkit-transition: height 500ms ease-in-out;
    -moz-transition: height 500ms ease-in-out;
    -ms-transition: height 500ms ease-in-out;
    -o-transition: height 500ms ease-in-out;
    transition: height 500ms ease-in-out;
}

.owl-carousel .owl-item{
    float: left;
}
.owl-controls .owl-page,
.owl-controls .owl-buttons div{
    cursor: pointer;
}
.owl-controls {
    -webkit-user-select: none;
    -khtml-user-select: none;
    -moz-user-select: none;
    -ms-user-select: none;
    user-select: none;
    -webkit-tap-highlight-color: rgba(0, 0, 0, 0);
}

/* mouse grab icon */
.grabbing { 
    cursor:url(grabbing.png) 8 8, move;
}

/* fix */
.owl-carousel  .owl-wrapper,
.owl-carousel  .owl-item{
    -webkit-backface-visibility: hidden;
    -moz-backface-visibility:    hidden;
    -ms-backface-visibility:     hidden;
  -webkit-transform: translate3d(0,0,0);
  -moz-transform: translate3d(0,0,0);
  -ms-transform: translate3d(0,0,0);
}
TylerH
  • 20,799
  • 66
  • 75
  • 101
Mahdi Bashirpour
  • 17,147
  • 12
  • 117
  • 144
-1

You don't need to do anything with the jQuery anymore to show owl-carousel into the bootstrap tab.

If you want to take owl-carousel into the tab then you should give same IDs to each owl carousel with same class="owl-carousel".

Codepen

jQuery(document).ready(function() {
  jQuery(".owl-carousel").owlCarousel();
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="container">
  <div class="row">
    <div class="col-xs-12">

      <div>

        <!-- Nav tabs -->
        <ul class="nav nav-tabs" role="tablist">
          <li role="presentation" class="active"><a href="#home" aria-controls="home" role="tab" data-toggle="tab">Home</a></li>
          <li role="presentation"><a href="#profile" aria-controls="profile" role="tab" data-toggle="tab">Profile</a></li>
        </ul>

        <!-- Tab panes -->
        <div class="tab-content">
          <div role="tabpanel" class="tab-pane active" id="home">
            <div id="owl-example" class="owl-carousel">
              <div> <img src="https://www.fillmurray.com/640/360"> </div>
              <div> <img src="https://www.fillmurray.com/640/360"> </div>
              <div> <img src="https://www.fillmurray.com/640/360"> </div>
              <div> <img src="https://www.fillmurray.com/640/360"> </div>
              <div> <img src="https://www.fillmurray.com/640/360"> </div>
              <div><img src="https://www.fillmurray.com/640/360"> </div>
              <div> <img src="https://www.fillmurray.com/640/360"> </div>
            </div>
          </div>
          <div role="tabpanel" class="tab-pane" id="profile">
            <div id="owl-example" class="owl-carousel">
              <div> <img src="https://loremflickr.com/640/360"> </div>
              <div> <img src="https://loremflickr.com/640/360"> </div>
              <div> <img src="https://loremflickr.com/640/360"> </div>
              <div> <img src="https://loremflickr.com/640/360"> </div>
              <div> <img src="https://loremflickr.com/640/360"> </div>
              <div> <img src="https://loremflickr.com/640/360"> </div>
              <div> <img src="https://loremflickr.com/640/360"> </div>
            </div>
          </div>
        </div>

      </div>

    </div>
  </div>
</div>
double-beep
  • 5,031
  • 17
  • 33
  • 41
Mayank Dudakiya
  • 3,635
  • 35
  • 35
-1

I have solve the problem in the way,


    $("ul .nav-link").on("click", function(){
        $("ul .nav-item").each(function(i,e){
          $(e).find(".active").removeClass("active");
        });

    });
Rubel Hossain
  • 2,503
  • 2
  • 22
  • 23