简体   繁体   中英

bug in next and prev buttons of carousel

i create 2 carousels. Both are clone with the same.css and.js file but the problem is that the fist carousel's next and prev buttons are working properly bu the second carousel's next and prev button are not working. Why this is happen.can you please solve it. I also tried by renaming second carousel's classes and id's, and make another css file and js for it. but it is again not working. please say what Can u do. here is html file

<div id="wrapper">
    <div id="carousel">
        <div id="content">
            <a href=""> <img class="item" src="images/b1.jpg" /></a>
            <a href=""> <img class="item" src="images/images (2).jpeg" /></a>
        </div>
    </div>
    <button id="prev">
        <svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24">
            <path fill="none" d="M0 0h24v24H0V0z" />
            <path d="M15.61 7.41L14.2 6l-6 6 6 6 1.41-1.41L11.03 12l4.58-4.59z" />
        </svg>
    </button>
    <button id="next">
        <svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24">
            <path fill="none" d="M0 0h24v24H0V0z" />
            <path d="M10.02 6L8.61 7.41 13.19 12l-4.58 4.59L10.02 18l6-6-6-6z" />
        </svg>
    </button>
</div>

<div id="wrapper">
    <div id="carousel">
        <div id="content">
            <a href=""> <img class="item" src="images/b1.jpg" /></a>
            <a href=""> <img class="item" src="images/images (2).jpeg" /></a>
        </div>
    </div>
    <button id="prev">
        <svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24">
            <path fill="none" d="M0 0h24v24H0V0z" />
            <path d="M15.61 7.41L14.2 6l-6 6 6 6 1.41-1.41L11.03 12l4.58-4.59z" />
        </svg>
    </button>
    <button id="next">
        <svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24">
            <path fill="none" d="M0 0h24v24H0V0z" />
            <path d="M10.02 6L8.61 7.41 13.19 12l-4.58 4.59L10.02 18l6-6-6-6z" />
        </svg>
    </button>
</div>

CSS

#wrapper {
  width: 100%;
  max-width: 964px;
  position: relative;
}

#carousel {
  overflow: auto;
  scroll-behavior: smooth;
  scrollbar-width: none;
}

#carousel::-webkit-scrollbar {
  height: 0;
}

#prev,
#next {
  display: flex;
  justify-content: center;
  align-content: center;
  background: white;
  border: none;
  padding: 8px;
  border-radius: 50%;
  outline: 0;
  cursor: pointer;
  position: absolute;
}

#prev {
  top: 50%;
  left: 0;
  transform: translate(50%, -50%);
  display: none;
}

#next {
  top: 50%;
  right: 0;
  transform: translate(-50%, -50%);
}

#content {
  display: grid;
  grid-gap: 16px;
  grid-auto-flow: column;
  margin: auto;
  box-sizing: border-box;
}

.item {
  width: 200px;
  height: 250px;
  background: green;
}

JavaScript

const gap = 16;
const carousel = document.getElementById("carousel"),
  content = document.getElementById("content"),
  next = document.getElementById("next"),
  prev = document.getElementById("prev");

next.addEventListener("click", e => {
  carousel.scrollBy(width + gap, 0);
  if (carousel.scrollWidth !== 0) {
    prev.style.display = "flex";
  }
  if (content.scrollWidth - width - gap <= carousel.scrollLeft + width) {
    next.style.display = "none";
  }
});
prev.addEventListener("click", e => {
  carousel.scrollBy(-(width + gap), 0);
  if (carousel.scrollLeft - width - gap <= 0) {
    prev.style.display = "none";
  }
  if (!content.scrollWidth - width - gap <= carousel.scrollLeft + width) {
    next.style.display = "flex";
  }
});

let width = carousel.offsetWidth;
window.addEventListener("resize", e => (width = carousel.offsetWidth));
              
           

here first carousel is perfact but seconds next and prev buttons are not working..even everything is same.

As said in the comments, ALL id's on a page have to be unique, otherwhise always the first one is targeted. To make it work with multiple buttons you have to set up a bit more flexible system.

Your prev and next buttons are wrapped inside a wrapper div that also contains carousel and content , so you don't need any id at all. You can target them using the DOM functions of javascript if you know what button is clicked. And for that there is the handy event.target .

Use classes to style the div's (note all id's are gone):

<div class="wrapper">
   <div class="carousel">
      <div class="content">
      ....
      </div>
   </div>
   <button class="prev">...</button>
   <button class="next">...</button>
</div>

To bind an eventlistener to the two (or more!) next buttons, you then use a queryselector looking for all elements with a class named next . You can use that to bind an eventlistener to all the next buttons:

var all_next = document.querySelectorAll(".next");
all_next.forEach( function(el){
    el.addEventListener( "click", function(event){
       //get the clicked button
       var clicked_element = e.target;
       // do something here
       .... 
    }
 })

From the line var clicked_element = e.target; you now know exactly which button is clicked and work out what wrapper, carousel and container are connected with that:

//get the wrapper (is the parent of NEXT)
  var wrapper = clicked_element.parentNode;
//get the carousel (is first child of wrapper)
  var carousel = wrapper.children[0];
//get the content (is first child of carousel)
  var content = carousel.children[0];

Now you can do your magic on the required elements.

Repeat this for the prev buttons.

It might seem a bit more work at first, but you are know much more flexible. You can add additional wrappers without having to work out if the id isn't in use yet.

NOTE There might be typo's in this answer.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM