Creating an Image Slider with HTML, CSS, and JavaScript
Tags: html, css, javascript, tutorial
Published: 2023-11-20 04:23:40

In this article, we are going to discuss how to build an image slider using HTML, CSS, and JavaScript. I will demonstrate two different ways to create the slider, one `opacity` based and the other `transform` based.

> 📧 [Subscribe to my newsletter to get the source code for FREE!](https://ericsdevblog.ck.page/source-code)

## Creating HTML

Let's first start with the HTML code:

```html
<div class="slider">
  <div class="slide">
    <img src="images/1.jpg" alt="demo image" />
  </div>
  <div class="slide">
    <img src="images/2.jpg" alt="demo image" />
  </div>
  . . .
  <a class="prev" onclick="prevSlide()">&lt;</a>
  <a class="next" onclick="nextSlide()">&gt;</a>
</div>
```

- `.slider` act as the container for the entire image slider.
- Individual slide is enclosed in a `.slide` container along with the image.
- The slider navigation is controlled by two links, `.prev` and `.next`.

We also have the `onclick` event listener set up for the navigation links, and when they are clicked, the corresponding JavaScript functions will be activated.

## Adding styles

For easier styling of elements, it is recommended to remove the default paddings and margins of all elements, and [set `box-sizing` to `border-box`](https://www.ericsdevblog.com/courses/html-css/3/#box-sizing). This allows the elements to be sized based on their `border-box` dimensions rather than `content-box`.

```css
* {
  padding: 0px;
  margin: 0px;
  box-sizing: border-box;
}
```

And then add the styles for the `.slider`.

```css
.slider {
  width: 500px;
  height: 300px;
  margin: auto;
  overflow: hidden;
  transform: translateY(50%);
}
```

As well as individual `.slide`.

```css
.slide {
  position: absolute;
  top: 50%;
  transform: translateY(-50%);
}

img {
  width: 100%;
  height: auto;
}
```

The highlighted lines are used to center `.slide` inside the `.slider` container. For details on [how to center a `<div>`](https://www.ericsdevblog.com/posts/how-to-center-a-div-in-css/), please refer to the linked article.

Lastly, we'll also place the navigation links on the left and right side of the `.slider` container.

```css
.prev,
.next {
  cursor: pointer;
  background-color: #333;
  color: #fff;
  padding: 10px 20px;
  position: absolute;
  top: 50%;
  transform: translateY(-50%);
  text-decoration: none;
}

.prev {
  left: 0;
}

.next {
  right: 0;
}
```

Here is a detailed tutorial on [how to place and arrange content using CSS](https://www.ericsdevblog.com/courses/html-css/4/) if you need more assistance.

## Adding JavaScript code

Now, let's take a closer look at the styles for each individual `.slide`.

```css
.slide {
  position: absolute;
  top: 50%;
  transform: translateY(-50%);
}
```

By using the [`absolute` position](https://www.ericsdevblog.com/courses/html-css/4/#absolute-position), we placed all individual `.slide`s in one location, stacked on top of each other. You can verify that using the developer tools in your browser.

![slide stack](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/wlmgfw3eadv3265bp9yz.gif)

To reveal the image underneath, all we need to do is setting the `opacity` of the current slide to `100`, while setting the `opacity` of all other slides to `0`. And to achieve the slideshow effect, we can write our JavaScript code so that whenever a navigation link is clicked, the "current slide" adjusts accordingly.

We'll start by setting the `opacity` of all slides to `0` by default.

```css
.slide {
  position: absolute;
  top: 50%;
  transform: translateY(-50%);

  opacity: 0;
  transition: opacity 1s ease;
}
```

And then add the following JavaScript code.

```javascript
const slides = document.querySelectorAll(".slide");
let currentSlide = 0;

function showSlide(index) {
  slides.forEach((slide, i) => {
    if (i === index) {
      slide.style.opacity = 100;
    } else {
      slide.style.opacity = 0;
    }
  });
}

function nextSlide() {
  currentSlide = (currentSlide + 1) % slides.length;
  showSlide(currentSlide);
}

function prevSlide() {
  currentSlide = (currentSlide - 1 + slides.length) % slides.length;
  showSlide(currentSlide);
}

showSlide(currentSlide);
```

Line 1 selects all `.slide`s, and assigns them to the variable `slides`.

Line 2 initiates the variable `currentSlide` to be `0`, which points to the first slide in the image slider.

Now, let's take a look at the `nextSlide()` function.

```javascript
function nextSlide() {
  currentSlide = (currentSlide + 1) % slides.length;
  showSlide(currentSlide);
}
```

In this case, `slides.length` gives the total number of slides in the slider, and when this function is executed (by clicking the `.next` link), the `currentSlide` will be adjusted accordingly.

For example, when the function is executed the first time, assuming there are 5 slides in total:

```text
currentSlide = (0 + 1) % 5 = 1
```

But when it is executed the fifth time, `currentSlide` will reset back to `0`.

```text
currentSlide = (4 + 1) % 5 = 0
```

The `prevSlide()` function works similarly.

```javascript
function prevSlide() {
  currentSlide = (currentSlide - 1 + slides.length) % slides.length;
  showSlide(currentSlide);
}
```

When `currentSlide` is `4`, which points to the fifth slide:

```text
currentSlide = (4 - 1 + 5) % 5 = 3
```

When `currentSlide` is `0`, which points to the first slide:

```text
currentSlide = (0 - 1 + 5) % 5 = 4
```

The `currentSlide` variable will then be passed to the `showSlide()` function as the `index`.

```javascript
function showSlide(index) {
  slides.forEach((slide, i) => {
    if (i === index) {
      slide.style.opacity = 100;
    } else {
      slide.style.opacity = 0;
    }
  });
}
```

This function iterates over all slides stored in `slides`, and if the iteration index (`i`) matches the `currentSlide` index (`index`), then that slide will have its `opacity` set to `100`. If not, its `opacity` will be `0`.

This will be the final result ⬇️

![opacity transition](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/xtjz35sghddr02vj1vtm.gif)

## Sliding with CSS transform

We called it an image slider, but as you can see from the final result, there is not much sliding because the transition is based on opacity. How can we adjust our code so that when the navigation link is clicked, the image actually slides over to the next?

![transform transition](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ngv2pqf0zpiancsypcu7.gif)

There are two alterations you must make. First, the `.slide`s must be arranged horizontally behind the `.slider` container, instead of stacked on top of each other. You can think of the `.slider` container as a window. Every time a link is clicked, the `.slide`s get shifted left or right to reveal the previous or the next image.

```css
.slider {
  width: 500px;
  height: 300px;
  margin: auto;
  overflow: hidden;
  transform: translateY(50%);

  display: flex;
  align-items: center;
}

.slide {
  flex: 0 0 100%;
  transition: transform 1s ease;
}
```

We are using a [flex layout](https://www.ericsdevblog.com/courses/html-css/4/#flexbox-layout) to achieve this effect. `flex: 0 0 100%` set the width of each `.slide` to be 100% of the `.slider`.

Next, adjust the `showSlide()` function.

```javascript
function showSlide(index) {
  slides.forEach((slide, i) => {
    const slideWidth = slide.clientWidth;
    slide.style.transform = `translateX(-${index * slideWidth}px)`;
  });
}
```

Again, assuming there are five slides in total, and each slide is `500px` wide. When index is `3`, `index * slideWidth` would be `1500`, and `translateX(-1500px)` will shift all `.slide`s to the left by `1500` pixels, revealing the fourth image.

## Conclusion

In this article, we demonstrated two ways to build an image slider, one opacity-based, and the other transform-based. I hope this article has been helpful to you. If you need more assistance regarding HTML and CSS, check out my course _[HTML & CSS: A Practical Guide](https://www.ericsdevblog.com/courses/html-css/)_.

That's all for this article. Happy coding!

Here are some of my other articles if you are interested:

- [HTML & CSS: A Practical Guide](https://www.ericsdevblog.com/courses/html-css/)
- [CSS and Responsive Design](https://www.ericsdevblog.com/courses/html-css/5/)
- [How to Center A Div in CSS](https://www.ericsdevblog.com/posts/how-to-center-a-div-in-css/)
- [How to Optimize Your Website](https://www.ericsdevblog.com/posts/how-to-optimize-your-website/)
- [Delve into CSS Grid and Flexbox](https://levelup.gitconnected.com/delve-into-css-grids-and-flexboxes-eba532677bab)
- [How to Create Transitions and Animations Using CSS](https://levelup.gitconnected.com/how-to-create-transitions-and-animations-using-css-f5fff20dcaa2)
- [How to Position and Align Elements Using CSS](https://levelup.gitconnected.com/how-to-position-and-align-elements-using-css-73db2ef3d6ac)
- [Working with Typography in CSS](https://blog.devgenius.io/working-with-typography-in-css-ca700859fe27)
- [Three Ways of Defining Colors in CSS](https://medium.com/devdive/three-ways-of-defining-colors-in-css-7b2f98a3fbf3)