<section class="section">
<div class="container">
<div class="testimonials">
<div class="testimonials__left">
<div class="testimonials__text">
<h2>Some of our happy customers</h2>
<p>Amet minim mollit non deserunt ullamco est sit aliqua dolor do amet sint. Velit officia consequat duis enim velit mollit. Exercitation veniam consequat sunt nostrud amet.</p>
</div>
</div>
<div class="testimonials__right">
<div class="carousel">
<div class="quote-card carousel__cell">
<img class="quote-card__image" src="https://assets.codepen.io/2479807/person-1.png" />
<div class="quote-card__text">
<p>Amet minim mollit non deserunt ullamco est sit aliqua dolor do amet.</p>
<p class="small-caps">Brooklyn Simmons</p>
</div>
</div>
<div class="quote-card carousel__cell">
<img class="quote-card__image" src="https://assets.codepen.io/2479807/person-2.png" />
<div class="quote-card__text">
<p>Amet minim mollit non deserunt ullamco est sit aliqua dolor do amet.</p>
<p class="small-caps">Wade Warren</p>
</div>
</div>
<div class="quote-card carousel__cell">
<img class="quote-card__image" src="https://assets.codepen.io/2479807/person-3.png" />
<div class="quote-card__text">
<p>Amet minim mollit non deserunt ullamco est sit aliqua dolor do amet.</p>
<p class="small-caps">Jenny Wilson</p>
</div>
</div>
<div class="quote-card carousel__cell">
<img class="quote-card__image" src="https://assets.codepen.io/2479807/person-4.png" />
<div class="quote-card__text">
<p>Amet minim mollit non deserunt ullamco est sit aliqua dolor do amet.</p>
<p class="small-caps">Marlyn Johnson</p>
</div>
</div>
<div class="quote-card carousel__cell">
<img class="quote-card__image" src="https://assets.codepen.io/2479807/person-1.png" />
<div class="quote-card__text">
<p>Amet minim mollit non deserunt ullamco est sit aliqua dolor do amet.</p>
<p class="small-caps">Brooklyn Simmons</p>
</div>
</div>
<div class="quote-card carousel__cell">
<img class="quote-card__image" src="https://assets.codepen.io/2479807/person-2.png" />
<div class="quote-card__text">
<p>Amet minim mollit non deserunt ullamco est sit aliqua dolor do amet.</p>
<p class="small-caps">Wade Warren</p>
</div>
</div>
<div class="quote-card carousel__cell">
<img class="quote-card__image" src="https://assets.codepen.io/2479807/person-3.png" />
<div class="quote-card__text">
<p>Amet minim mollit non deserunt ullamco est sit aliqua dolor do amet.</p>
<p class="small-caps">Jenny Wilson</p>
</div>
</div>
<div class="quote-card carousel__cell">
<img class="quote-card__image" src="https://assets.codepen.io/2479807/person-4.png" />
<div class="quote-card__text">
<p>Amet minim mollit non deserunt ullamco est sit aliqua dolor do amet.</p>
<p class="small-caps">Marlyn Johnson</p>
</div>
</div>
</div>
</div>
</div>
</div>
</section>
<div class="extra"></div>
@font-face {
src: url("https://assets.codepen.io/2479807/gilroy-regular.ttf");
font-family: "Gilroy";
}
@font-face {
src: url("https://assets.codepen.io/2479807/gilroy-semibold.woff2");
font-family: "Gilroy Semi-Bold";
}
html {
box-sizing: border-box;
}
*,
*:after,
*:before {
margin: 0;
padding: 0;
box-sizing: inherit;
outline: none;
}
img,
embed,
iframe,
object,
video {
display: block;
max-width: 100%;
border-style: none;
}
input,
textarea,
select,
button {
color: inherit;
font: inherit;
letter-spacing: inherit;
border: none;
background: none;
}
@mixin dropShadow {
box-shadow: 0 1px 2px rgba(0, 0, 0, 0.02), 0 2px 4px rgba(0, 0, 0, 0.02),
0 4px 8px rgba(0, 0, 0, 0.02), 0 8px 16px rgba(0, 0, 0, 0.02),
0 16px 32px rgba(0, 0, 0, 0.02), 0 32px 64px rgba(0, 0, 0, 0.02);
}
:root {
--color-primary: #003a44;
--color-tertiary: #dbf4ee;
--heading-color-dark: #003a44;
--text-color-dark: #5b797c;
--border-radius: 10px;
}
body {
font-family: "Gilroy", sans-serif;
font-size: 16px;
text-rendering: optimizeLegibility;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
line-height: 1.5;
color: var(--text-color-dark);
}
.small-caps {
font-family: "Gilroy Semi-Bold";
font-size: 14px;
letter-spacing: 0.05em;
text-transform: uppercase;
}
%heading {
color: var(--heading-color-dark);
}
h2 {
@extend %heading;
font-size: 40px;
font-family: "Gilroy Semi-Bold";
line-height: 1.2;
margin-bottom: 32px;
}
.container {
max-width: 1400px;
margin: 0 auto;
padding: 0 80px;
}
.testimonials {
position: relative;
display: flex;
justify-content: space-between;
align-items: center;
//min-height: 100vh;
//padding: 160px 0;
@media (max-width: 940px) {
flex-direction: column;
justify-content: initial;
align-items: flex-start;
}
&__left {
width: 50%;
}
&__right {
left: 50%;
width: 50%;
@media (max-width: 940px) {
position: relative;
top: 0;
left: 0;
width: 100%;
}
}
&__text {
max-width: 400px;
}
}
.quote-card {
display: flex;
background-color: var(--color-tertiary);
padding: 32px 80px;
border-radius: var(--border-radius);
&:nth-child(even) {
//transform: translateX(15%);
}
&__image {
width: 64px;
height: 64px;
margin-right: 32px;
}
}
.carousel {
position: absolute;
height: 100%;
width: 100%;
&__cell {
visibility: hidden;
&[data-active] {
visibility: visible;
opacity: 1;
}
}
&__wrapper {
position: relative;
top: 0;
left: 0;
width: 100%;
height: 100%;
}
}
.extra {
height: 0;
background-color: white;
}
View Compiled
// Work in progress
window.addEventListener("load", () => {
const carousel = document.querySelector(".carousel");
class Slider {
constructor(options) {
if (!options.container) return;
this.container = options.container;
this.speed = options.speed || 1;
this.ease = options.ease || "power3.inOut";
this.spacing = options.spacing || 32;
this.autoPlay = options.autoPlay || 3000;
this.visibleCells = options.visibleCells || 4;
this.padding = options.padding || 160;
this.cells = [...this.container.children];
this.init();
}
init() {
this._setParentWrapper(
this.container,
this._setInitialStates.bind(this)
);
this._setParentStyles();
//this._moveCells();
this._onWindowResize();
this.startLoop();
}
_setParentWrapper(toWrap, _callback) {
this.wrapper = document.createElement("div");
this.wrapper.classList.add("carousel__wrapper");
toWrap.parentNode.appendChild(this.wrapper);
this.wrapper.appendChild(toWrap);
_callback();
}
async _setParentStyles() {
let cardsHeight = 0;
for (let i = 0; i < this.visibleCells; i++) {
cardsHeight +=
this.cells[i].getBoundingClientRect().height + this.spacing;
}
this.wrapper.style.height = `${
cardsHeight - this.spacing + this.padding * 2
}px`;
}
_setInitialStates() {
this.cellHeight = this.cells[0].getBoundingClientRect().height;
this.restingPosition = this.cellHeight * this.visibleCells;
this.cells.forEach(async (cell, index) => {
cell.style.position = "absolute";
if (index < this.visibleCells) {
gsap.set(cell, {
y: (this.cellHeight + this.spacing) * index
});
cell.setAttribute("data-active", "");
} else {
gsap.set(cell, {
y: this.restingPosition,
autoAlpha: 0
});
}
});
}
_fadeCellOut(cell) {
gsap.to(cell, {
y: -this.cellHeight,
autoAlpha: 0,
duration: this.speed,
ease: this.ease,
onComplete: () => {
gsap.set(cell, {
y: this.restingPosition
});
this.container.appendChild(cell);
cell.removeAttribute("data-active");
}
});
}
_fadeCellIn(cell) {
gsap.to(cell, {
y: "-=" + (this.cellHeight + this.spacing),
autoAlpha: 1,
duration: this.speed,
ease: this.ease,
onStart: () => {
cell.setAttribute("data-active", "");
}
});
}
_moveCellsUp(activeCells) {
gsap.to(activeCells, {
y: "-=" + (this.cellHeight + this.spacing),
duration: this.speed,
ease: this.ease
});
}
async _moveCells() {
this.activeCells = [...document.querySelectorAll("[data-active]")];
const firstCell = this.container.querySelector(".carousel__cell");
const middleCells = this.activeCells.filter(
(cell, index) => index !== 0 && index !== this.length - 1
);
const nextCell = this.activeCells[middleCells.length]
.nextElementSibling;
this._fadeCellOut(firstCell);
this._moveCellsUp(middleCells);
this._fadeCellIn(nextCell);
}
startLoop() {
this.loop = setInterval(() => {
this._moveCells();
}, 5000);
}
stopLoop() {
clearInterval(this.loop);
}
_debounce(func, wait) {
let timeout;
return function executedFunction(...args) {
const later = () => {
clearTimeout(timeout);
func(...args);
};
clearTimeout(timeout);
timeout = setTimeout(later, wait);
};
}
_onWindowResize() {
const reset = this._debounce(() => {
this.stopLoop();
gsap.set(this.cells, {
autoAlpha: 1,
clearProps: "y",
onComplete: this._setInitialStates.bind(this)
});
}, 500);
window.addEventListener("resize", () => {
gsap.set(this.cells, {
autoAlpha: 0
});
reset();
});
}
}
const slider = new Slider({
container: carousel,
speed: 1,
ease: "power3.inOut",
spacing: 32,
visibleCells: 4,
padding: 160
});
});
View Compiled
This Pen doesn't use any external CSS resources.