Fancy Animated Photo Slideshow with jQuery and Greensock

File Size: 7.91 KB
Views Total: 2683
Last Update:
Publish Date:
Official Website: Go to website
License: MIT
   
Fancy Animated Photo Slideshow with jQuery and Greensock

A cool, fullscreen, responsive, animated image slideshow / carousel with a nifty gallery browser, built with jQuery, CSS3 and Greensock's TweenMax.js.

See it in action:

How to use it:

1. Build the markup structure and add your images to the slideshow as shown below:

<div class="slideshow">
  <div class="slideshow__contentWrap">
    <h2 class="slideshow__title">Slideshow Tittle</h2>
    <p class="slideshow__text">Slideshow Description</p>
  </div>
  <ul class="slideshow__container">
    <li class="slideshow__item">
      <img src="1.jpg" class="slideshow__image"/>
    </li>
    <li class="slideshow__item">
      <img src="2.jpg" class="slideshow__image"/>
    </li>
    <li class="slideshow__item">
      <img src="3.jpg" class="slideshow__image"/>
    </li>
    <li class="slideshow__item">
      <img src="4.jpg" class="slideshow__image"/>
    </li>
  </ul>
  <div class="slideshow__back">
    <div class="slideshow__slidein">
      <div class="overlay"></div>
      <img src="4.jpg" class="slideshow__image"/>
      <h2 class="slideTitle">PREVIOUS SLIDE  </h2>
    </div>
    <div class="slideshow__block">
      <img src="close.png" class="close"/>
    </div>
    <div class="slideshow__prev">
      <svg width="32px" height="32px" viewBox="1 -1 32 32" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:sketch="http://www.bohemiancoding.com/sketch/ns">
        <g id="Page-1" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd" sketch:type="MSPage">
          <g id="prevBtn" sketch:type="MSArtboardGroup" stroke="#1B2023" stroke-width="2">
            <g id="Btn" sketch:type="MSLayerGroup" transform="translate(16.000000, 16.000000) scale(-1, 1) translate(-16.000000, -16.000000) ">
              <path d="M16,1 L25.6,16.5428571 L16,31" class="line" stroke-linecap="round" sketch:type="MSShapeGroup"></path>
              <circle class="circle" sketch:type="MSShapeGroup" cx="15" cy="15" r="15"></circle>
            </g>
          </g>
        </g>
      </svg>
      
    </div>
  </div>
  <div class="slideshow__forward">
    <div class="slideshow__slidein">
      <div class="overlay"></div>
      <img src="2.jpg" class="slideshow__image"/>
      <h2 class="slideTitle">NEXT SLIDE</h2>
    </div>
    <div class="slideshow__block">
      <img src="close.png" class="close"/>
    </div>
    <div class="slideshow__next">
      <svg width="32px" height="32px" viewBox="-1 -1 32 32" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" xmlns:sketch="http://www.bohemiancoding.com/sketch/ns">
        <g id="Page-1" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd" sketch:type="MSPage">
          <g class="Btn" sketch:type="MSLayerGroup" stroke="#1B2023" stroke-width="2">
            <path class="line" d="M16,1 L25.6,16.5428571 L16,31" class="line" stroke-linecap="round" sketch:type="MSShapeGroup"></path>
            <circle class="circle" sketch:type="MSShapeGroup" cx="15" cy="15" r="15"></circle>
          </g>
        </g>
      </svg>
    </div>
  </div>
</div>

2. The core CSS / CSS3 styles for the slideshow.

* { box-sizing: border-box; }

body {
  margin: 0;
  width: 100%;
  height: 100%;
  background-color: #fff;
  color: #fff;
  font-family: "Perpetua", serif;
}

.slideshow {
  width: 100%;
  height: 100vh;
  position: relative;
  overflow: hidden;
}

.slideshow__contentWrap {
  width: 500px;
  position: absolute;
  left: 50%;
  top: 50%;
  transform: translate(-50%, -50%);
  z-index: 2;
  text-align: center;
}

.slideshow__title {
  font-size: 4em;
  margin: 0;
  font-weight: 100;
}

.slideshow__text {
  font-size: 1em;
  line-height: 1.5;
  font-weight: 100;
  font-family: "Century Gothic", sans-serif;
}

.slideshow__container {
  display: block;
  list-style: none;
  position: relative;
  white-space: nowrap;
  height: 100%;
  width: 100%;
  padding: 0;
  margin: 0;
  font-size: 0;
}

.slideshow__item {
  display: inline-block;
  position: relative;
  width: 100%;
  height: 100%;
}

.slideshow__image {
  display: block;
  position: relative;
  height: auto;
  width: 100%;
  background-size: contain;
}

.slideshow__slidein {
  height: 100px;
  width: 350px;
  display: block;
  position: absolute;
  background-color: #000;
  top: 50%;
  transform: translateY(-50%);
  margin: 0;
  overflow: hidden;
}

.slideshow__slidein img {
  display: block;
  position: absolute;
  top: 50%;
  transform: translateY(-50%);
}

.slideshow .overlay {
  position: fixed;
  top: 0;
  left: 0;
  height: 100%;
  width: 100%;
  z-index: 10;
  background-color: #000;
  opacity: 0.5;
}

.slideshow__forward .slideshow__slidein {
  right: -350px;
  z-index: 2;
}

.slideshow__forward .slideshow__slidein .slideTitle {
  font-size: 1.5em;
  color: #fff;
  font-family: "Century Gothic", sans-serif;
  font-weight: 100;
  margin: 0;
  padding-left: 1em;
  position: relative;
  top: 50%;
  transform: translateY(-50%);
  z-index: 11;
  margin-right: 300px;
  text-align: right;
}

.slideshow__forward .slideshow__block {
  position: absolute;
  display: block;
  top: 50%;
  transform: translateY(-50%);
  height: 100px;
  width: 80px;
  right: 270px;
  opacity: 0;
  background-color: #fff;
  z-index: 2;
}

.slideshow__back .slideshow__slidein {
  left: -350px;
  z-index: 2;
}

.slideshow__back .slideshow__slidein .slideTitle {
  font-size: 1.5em;
  color: #fff;
  font-family: "Century Gothic", sans-serif;
  font-weight: 100;
  margin: 0;
  padding-right: 1em;
  float: right;
  position: relative;
  top: 50%;
  transform: translateY(-50%);
  z-index: 11;
  margin-left: 300px;
  text-align: right;
}

.slideshow__back .slideshow__block {
  position: absolute;
  display: block;
  top: 50%;
  transform: translateY(-50%);
  height: 100px;
  width: 80px;
  left: 270px;
  opacity: 0;
  background-color: #fff;
  z-index: 2;
}

.slideshow .close {
  width: 25px;
  height: 25px;
  position: relative;
  display: block;
  opacity: 0;
  transition: opacity .25s ease-in-out;
  top: 50%;
  transform: translateY(-50%);
  margin-left: auto;
  margin-right: auto;
}

.slideshow .slideshow__block:hover .close { opacity: 1; }

.slideshow__prev, .slideshow__next {
  width: 3em;
  z-index: 1;
}

.slideshow__prev svg, .slideshow__next svg {
  display: block;
  width: 100%;
  height: 100%;
}

.slideshow__prev {
  position: absolute;
  left: 5em;
  top: 50%;
  transform: translateY(-50%);
  cursor: pointer;
  z-index: 1;
}

.slideshow__prev .circle { opacity: 0; }

.slideshow__next {
  position: absolute;
  right: 5em;
  top: 50%;
  transform: translateY(-50%);
  cursor: pointer;
  z-index: 1;
}

.slideshow__next .circle { opacity: 0; }

3. Include the necessary jQuery and TweenMax.js JavaScript libraries at the bottom of the webpage.

<script src="TweenMax.min.js"></script> 
<script src="jquery-2.1.4.min.js"></script> 

4. The core JavaScript to active the slideshow.

$(document).ready(function() {
  var imgWidth = $(".slideshow__image").width(),
    $slider = $(".slideshow__container"),
    $nextButton = $(".slideshow__next"),
    $prevButton = $(".slideshow__prev"),
    closeBlock = $(".slideshow__block"),
    slideInBlock = (".slideshow__slidein"),
    slideNext = $('.slideshow__forward').find('.slideshow__slidein'),
    slideBack = $('.slideshow__back').find('.slideshow__slidein'),
    clickCount = 0,
    clickCountImg = 1;

  $nextButton.click(function() {
    var circle = $(this).find('.circle'),
      line = $(this).find('.line'),
      block = $(this).parent().find('.slideshow__block'),
      slideIn = $(this).parent().find('.slideshow__slidein'),
      tl = new TimelineMax({
        onComplete: tlComplete
      }),
      tl2 = new TimelineMax();

    tl.set(circle, {
        x: 15,
        y: 15,
        scale: 0
      })
      .set(slideIn, {
        right: -350,
        opacity: 1
      }, 0)
      .set(block, {
        right: 270,
        opacity: 0
      }, 0)
      .set($nextButton, {
        zIndex: 1
      }, 0)
      .to(circle, 0.5, {
        scale: 1,
        transformOrigin: "50%, 50%",
        opacity: 1
      }, 0)
      .to(circle, 0.3, {
        opacity: 0
      })
      .to(line, 0.3, {
        scale: 0,
        transformOrigin: "50%, 50%"
      }, 0)
      .set(circle, {
        scale: 0,
        opacity: 0
      });

    function tlComplete() {
      tl2.to(slideIn, 0.5, {
          right: 0
        })
        .to(block, 0.5, {
          right: 350,
          opacity: 1
        }, 0)
    };

    function getLineback() {
      TweenMax.to(line, 0.3, {
        scale: 1,
        opacity: 1,
        delay: 0.5
      });
    };

    closeBlock.click(function() {
      tl2.reverse();
    });

    closeBlock.click(getLineback);

    $prevButton.click(function() {
      tl2.reverse();
    });

    $prevButton.click(getLineback);

  });

  $prevButton.click(function() {
    var circle = $(this).find('.circle'),
      line = $(this).find('.line'),
      block = $(this).parent().find('.slideshow__block'),
      slideIn = $(this).parent().find('.slideshow__slidein'),
      tl = new TimelineMax({
        onComplete: tlComplete
      }),
      tl2 = new TimelineMax();

    tl.set(circle, {
        x: 15,
        y: 15,
        scale: 0
      })
      .set(slideIn, {
        left: -350,
        opacity: 1
      }, 0)
      .set(block, {
        left: 270,
        opacity: 0
      }, 0)
      .set($prevButton, {
        zIndex: 1
      }, 0)
      .to(circle, 0.5, {
        scale: 1,
        transformOrigin: "50%, 50%",
        opacity: 1
      }, 0)
      .to(circle, 0.3, {
        opacity: 0
      })
      .to(line, 0.3, {
        scale: 0,
        transformOrigin: "50%, 50%"
      }, 0)
      .set(circle, {
        scale: 0,
        opacity: 0
      });

    function tlComplete() {
      tl2.to(slideIn, 0.3, {
          left: 0
        })
        .to(block, 0.3, {
          left: 350,
          opacity: 1
        }, 0);
    };

    function getLineback() {
      TweenMax.to(line, 0.3, {
        scale: 1,
        opacity: 1,
        delay: 0.5
      });
    };

    closeBlock.click(function() {
      tl2.reverse();
    })

    closeBlock.click(getLineback);

    $nextButton.click(function() {
      tl2.reverse();
    });

    $nextButton.click(getLineback);

  });

  slideNext.click(function() {
    clickCount++;
    clickCountImg++;

    var clickCountImgPrev = clickCountImg - 2;
    var firstImage = $('.slideshow__container li img:eq(0)'),
      imagePrev = $('.slideshow__container li img:eq(' + clickCountImgPrev + ')'),
      image = $('.slideshow__container li img:eq(' + clickCountImg + ')');

    if (clickCount > 3) {
      clickCount = 0;
    }
    if (clickCountImg > 3) {
      clickCountImg = 0;
      firstImage.clone().appendTo(slideNext);
    }

    TweenMax.to($slider, 0.5, {
      x: -clickCount * imgWidth
    })

    slideNext.children("img").remove();
    slideBack.children("img").remove();
    image.clone().appendTo(slideNext);
    imagePrev.clone().appendTo(slideBack);
    console.log(image);

    if (clickCountImg == 0) {
      firstImage.clone().appendTo(slideNext);
    }

  });

  slideBack.click(function() {
    clickCount--;
    clickCountImg--;

    var clickCountImgPrev = clickCountImg - 2,
      firstImage = $('.slideshow__container li img:eq(0)'),
      imagePrev = $('.slideshow__container li img:eq(' + clickCountImgPrev + ')'),
      image = $('.slideshow__container li img:eq(' + clickCountImg + ')');

    if (clickCount < 0) {
      clickCount = 3;
    }

    if (clickCountImg < 0) {
      clickCountImg = 3;
    }

    TweenMax.to($slider, 0.5, {
      x: -clickCount * imgWidth
    });

    slideNext.children("img").remove();
    slideBack.children("img").remove();

    imagePrev.clone().appendTo(slideBack);
    image.clone().appendTo(slideNext);

  });
});

This awesome jQuery plugin is developed by baarte. For more Advanced Usages, please check the demo page or visit the official website.