Twitter Bootstrap Carousel slide duration

…衆ロ難τιáo~ 提交于 2019-12-18 07:00:07

问题


In the Twitter Bootstrap Carousel, how can I make a particular slide to have a different duration than others?

I can change the whole slider duration with the "interval" parameter, but don't know how to set a custom duration for a particular slide.


回答1:


Bootstrap 3.1 carousel don't allow diferent duration for each slide, but it offers one method and one event that we can use in order to ahieve this.

We will use the slid.bs.carousel event to detect when the carousel has completed its slide transition and the .carousel('pause') option to stop the carousel from cycling through items.

We will use this attribute data-interval="x" on each carousel item with different time duration, so our html will look like this for example:

<div class="carousel-inner">
    <div class="active item" data-interval="3000">
        <img src="Url 1" />
    </div>
    <div class="item" data-interval="6000">
        <img src="Url 2" />
    </div>
    <div class="item" data-interval="9000">
        <img src="Url 3" />
    </div>
</div>

Now, all we have to do is to:

  1. detect when a new item is displayed using the slid.bs.carousel event
  2. check his duration
  3. pause the carousel using .carousel('pause')
  4. set a timeout with the duration of the item and after the duration completed we should unpause the carousel

The javascript code will look like this:

var t;

var start = $('#myCarousel').find('.active').attr('data-interval');
t = setTimeout("$('#myCarousel').carousel({interval: 1000});", start-1000);

$('#myCarousel').on('slid.bs.carousel', function () {   
     clearTimeout(t);  
     var duration = $(this).find('.active').attr('data-interval');

     $('#myCarousel').carousel('pause');
     t = setTimeout("$('#myCarousel').carousel();", duration-1000);
})

$('.carousel-control.right').on('click', function(){
    clearTimeout(t);   
});

$('.carousel-control.left').on('click', function(){
    clearTimeout(t);   
});

As you can see, we are forced at the begining to add a starting interval and i've set it to 1000ms but i remove it each time i pause the carousel duration-1000. I've used the lines below to resolve the first item problem because that item was not caught by the slid event.

var start = $('#myCarousel').find('.active').attr('data-interval');
t = setTimeout("$('#myCarousel').carousel({interval: 1000});", start-1000);

I also noticed that if the user presses the arrows, the timeout is going crazy, that's why i clear the timeout each time the user press on the left and right arrow.

Here is my live example http://jsfiddle.net/paulalexandru/52KBT/, hope this response was helpful for you.




回答2:


You need to set interval in main div as data-interval tag. So it is working fine and you can give different time to different slides.

<!--main div -->
<div data-ride="carousel" class="carousel slide" data-interval="100" id="carousel-example-generic">
  <!-- Indicators -->
  <ol class="carousel-indicators">
    <li data-target="#carousel-example-generic" data-slide-to="0" class=""></li>
  </ol>

  <!-- Wrapper for slides -->
  <div role="listbox" class="carousel-inner">
    <div class="item">
      <a class="carousel-image" href="#">
        <img alt="image" src="image.jpg">
      </a>
    </div>
  </div>
</div>



回答3:


I could not get carousel('pause') to work at all inside the bootstrap event handlers. I'm not sure why - potentially it was due to dynamically rendering the slides with KnockoutJS or perhaps a bug in Bootstrap (I'm guessing it's my code).

So in order to set an individual slide's interval independent of it's friends in the carousel I used the slid.bs.carousel event bubbled up in Bootstrap along with using setTimeout to set the interval based on the item's data-interval attribute and manually calling the carousel('next') method.

JS

// slide event
$('.carousel').on('slid.bs.carousel', function () {
    var carouselData = $(this).data('bs.carousel');
    var currentIndex = carouselData.getActiveIndex();

    window.setTimeout(function() {
        $('.carousel').carousel('next');
    }, $(carouselData.$items[currentIndex]).data('interval'));
});

// init carousel
$('.carousel').carousel({
    interval: false
});

// set initial timeout for active slide data-interval
window.setTimeout(function () {
    $('.carousel').carousel('next');
}, $('.carousel .active').data('interval'));

HTML

<div class="carousel">
  <div class="carousel-inner">
    <div id="slide1" class="item active" data-interval="5000">{{content}}</div>
    <div id="slide2" class="item" data-interval="10000">{{content}}</div>
    <div id="slide3" class="item" data-interval="10000">{{content}}</div>
  </div>
</div>

In this example #slide1 will be the initial slide in your carousel and show for 5 seconds. After 5 seconds it will slide to #slide2.

#slide2 will pause for 10 seconds before sliding to #slide3. And so on. And so on...




回答4:


If you still haven't found a solution, I have modified the Bootstrap carousel.js to add this functionality.

  1. Add optional attribute (data-interval) to "item" class element.

    <div class="active item" data-interval="6000">

  2. Modify carousel.js

    • Add flag to determine first cycle

      var Carousel = function (element, options) {
      this.$element    = $(element)
      this.$indicators = this.$element.find('.carousel-indicators')
      this.options     = options
      this.paused      =
      this.sliding     =
      this.interval    =
      this.$active     =
      this.$items      = null
      //[TODO Kevin] Added - BEGIN
      this.isFirstCycle= true
      //[TODO Kevin] Added - BEGIN
      
      this.options.pause == 'hover' && this.$element
      .on('mouseenter', $.proxy(this.pause, this))
      .on('mouseleave', $.proxy(this.cycle, this))
      }
      
    • Modify CYCLE function

       Carousel.prototype.cycle =  function (e) {
       e || (this.paused = false)
      
       this.interval && clearInterval(this.interval)
       //[TODO Kevin] Modified - BEGIN
       //this.options.interval && !this.paused && (this.interval = setInterval($.proxy(this.next, this), this.options.interval))
      
       if (this.options.interval && !this.paused) {
         var $active = this.$element.find('.item.active');
      
         /**CUSTOM ITEM INTERVAL**/
         if ($active.data('interval')) {
           var customInterval;
      
           /*On First Cycle*/
           if(this.isFirstCycle) {
             //Get ACTIVE ITEM interval
             customInterval = $active.data('interval');
             this.isFirstCycle = false;
      
           /*On Suceeding Cycles*/
           } else {
             //Get NEXT ITEM interval
             var $next = $active['next']();
      
             if (!$next.length) {
               if (!this.options.wrap) return this
               $next = this.$element.find('.item')['first']()
             }
      
             customInterval = $next.data('interval');
           }
      
           this.interval = setInterval($.proxy(this.next, this), customInterval);
      
         /**DEFAULT INTERVAL**/
         } else {
           this.interval = setInterval($.proxy(this.next, this), this.options.interval);
         }
       }
       //[TODO Kevin] Modified - END
      
       return this
       }
      

Sample: JS Fiddle



来源:https://stackoverflow.com/questions/14236516/twitter-bootstrap-carousel-slide-duration

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!