리빌효과
전체소스
HTML / CSS
<!DOCTYPE html>
<html lang="ko">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>패럴렉스 이펙트07</title>
<link rel="stylesheet" href="css/reset.css">
<link rel="stylesheet" href="css/Parallax.css">
<style>
.reveal > div,
.reveal > span {
opacity: 0;
}
.reveal.show > div,
.reveal.show > span {
animation: opacity 1s linear forwards;
}
.reveal {
position: relative;
}
.reveal::before {
content: '';
position: absolute;
left: 0;
top: 0;
width: 0;
height: 100%;
background-color: #fff;
z-index: 1;
}
.reveal.reveal-TWO::after {
content: '';
position: absolute;
left: 0;
top: 0;
width: 0;
height: 100%;
z-index: 1;
background-color: #adadad;
}
/* 1개 */
.reveal.show::before {
animation: reveal 1s cubic-bezier(0, 0.78, 0.58, 1);
}
.reveal.reveal-RTL.show::before {
animation: reveal-RTL 1s cubic-bezier(0, 0.78, 0.58, 1);
}
.reveal.reveal-TTB.show::before {
animation: reveal-TTB 1s cubic-bezier(0, 0.78, 0.58, 1);
}
.reveal.reveal-BTT.show::before {
animation: reveal-BTT 1s cubic-bezier(0, 0.78, 0.58, 1);
}
/* 2개 */
.reveal.show::after {
animation: reveal 1s 0.5s cubic-bezier(0, 0.78, 0.58, 1);
}
.reveal.reveal-RTL.show::after {
animation: reveal-RTL 1s 0.5s cubic-bezier(0, 0.78, 0.58, 1);
}
.reveal.reveal-TTB.show::after {
animation: reveal-TTB 1s 0.5s cubic-bezier(0, 0.78, 0.58, 1);
}
.reveal.reveal-BTT.show::after {
animation: reveal-BTT 1s 0.5s cubic-bezier(0, 0.78, 0.58, 1);
}
/* animation */
@keyframes opacity {
0% {opacity:0;}
60% {opacity:0;}
70% {opacity:1;}
100% {opacity:1;}
}
@keyframes reveal {
0% {width: 0; left: 0;}
50% {width: 100%; left: 0;}
80% {width: 100%; left: 0;}
100% {width: 0; left: 100%;}
}
@keyframes reveal-RTL {
0% {width: 0; left: auto; right: 0;}
50% {width: 100%; left: auto; right: 0;}
80% {width: 100%; left: auto; right: 0;}
100% {width: 0; left: auto; right: 100%;}
}
@keyframes reveal-TTB {
0% {width: 100%; height: 0; top: 0;}
50% {width: 100%; height: 100%; top: 0;}
80% {width: 100%; height: 100%; top: 0;}
100% {width: 100%; height: 0; top: 100%;}
}
@keyframes reveal-BTT {
0% {width: 100%; height: 0; bottom:0; top: auto;}
50% {width: 100%; height: 100%; bottom:0; top: auto;}
80% {width: 100%; height: 100%; bottom:0; top: auto;}
100% {width: 100%; height: 0; bottom:100%; top: auto;}
}
.Parallax__item__num,
.Parallax__item__title {
display: none;
}
</style>
</head>
<body class="img05 bg01 font09">
<header id="header">
<h1>Javascript Parallax Effect07</h1>
<p>패럴렉스 이펙트 : 리빌 효과</p>
<ul>
<li><a href="parallaxEffect01.html">1</a></li>
<li><a href="parallaxEffect02.html">2</a></li>
<li><a href="parallaxEffect03.html">3</a></li>
<li><a href="parallaxEffect04.html">4</a></li>
<li><a href="parallaxEffect05.html">5</a></li>
<li><a href="parallaxEffect06.html">6</a></li>
<li class="active"><a href="parallaxEffect07.html">7</a></li>
</ul>
</header>
<!-- header -->
<main id="main">
<div class="Parallax__wrap">
<section id="section1" class="Parallax__item">
<span class="Parallax__item__num">01</span>
<h2 class="Parallax__item__title">section1</h2>
<figure class="Parallax__item__imgWrap reveal">
<div class="Parallax__item__img"></div>
</figure>
<p class="Parallax__item__desc reveal">삶은 탐구하는 모험이다.</p>
</section>
<!-- //section1 -->
<section id="section2" class="Parallax__item">
<span class="Parallax__item__num">02</span>
<h2 class="Parallax__item__title">section2</h2>
<figure class="Parallax__item__imgWrap reveal">
<div class="Parallax__item__img"></div>
</figure>
<p class="Parallax__item__desc reveal">오늘 당신이 할 수 있는 최선의 일을 하라.</p>
</section>
<!-- //section2 -->
<section id="section3" class="Parallax__item">
<span class="Parallax__item__num">03</span>
<h2 class="Parallax__item__title">section3</h2>
<figure class="Parallax__item__imgWrap reveal reveal-RTL">
<div class="Parallax__item__img"></div>
</figure>
<p class="Parallax__item__desc reveal reveal-RTL">비난은 쓸모없는 짓이다.</p>
</section>
<!-- //section3 -->
<section id="section4" class="Parallax__item">
<span class="Parallax__item__num">04</span>
<h2 class="Parallax__item__title">section4</h2>
<figure class="Parallax__item__imgWrap reveal reveal-TTB">
<div class="Parallax__item__img"></div>
</figure>
<p class="Parallax__item__desc reveal reveal-TTB">우리의 삶은 우리가 생각하는 것처럼 빠르지 않고, 우리가 생각하는 것보다 짧다.</p>
</section>
<!-- //section4 -->
<section id="section5" class="Parallax__item">
<span class="Parallax__item__num">05</span>
<h2 class="Parallax__item__title">section5</h2>
<figure class="Parallax__item__imgWrap reveal reveal-BTT">
<div class="Parallax__item__img"></div>
</figure>
<p class="Parallax__item__desc reveal reveal-BTT">머리로 생각하는 것보다는 마음으로 생각하고 행동하라.</p>
</section>
<!-- //section5 -->
<section id="section6" class="Parallax__item">
<span class="Parallax__item__num">06</span>
<h2 class="Parallax__item__title">section6</h2>
<figure class="Parallax__item__imgWrap reveal reveal-TWO">
<div class="Parallax__item__img"></div>
</figure>
<p class="Parallax__item__desc reveal reveal-TWO"data-delay=1000>인생은 문제다. 그것을 해결해 나가는 과정에서 삶이 만들어진다.</p>
</section>
<!-- //section6 -->
<section id="section7" class="Parallax__item">
<span class="Parallax__item__num">07</span>
<h2 class="Parallax__item__title">section7</h2>
<figure class="Parallax__item__imgWrap reveal reveal-TWO reveal-RTL">
<div class="Parallax__item__img"></div>
</figure>
<p class="Parallax__item__desc reveal reveal-TWO reveal-RTL"data-delay=1000>성공은 단순히 실패를 거듭하고 계속하는 것이다.</p>
</section>
<!-- //section7 -->
<section id="section8" class="Parallax__item">
<span class="Parallax__item__num">08</span>
<h2 class="Parallax__item__title">section8</h2>
<figure class="Parallax__item__imgWrap reveal reveal-TWO reveal-TTB">
<div class="Parallax__item__img"></div>
</figure>
<p class="Parallax__item__desc reveal reveal-TWO reveal-TTB"data-delay=1000>기회는 항상 어려운 일 모습으로 찾아온다.</p>
</section>
<!-- //section8 -->
<section id="section9" class="Parallax__item">
<span class="Parallax__item__num">09</span>
<h2 class="Parallax__item__title">section9</h2>
<figure class="Parallax__item__imgWrap reveal reveal-TWO reveal-BTT">
<div class="Parallax__item__img"></div>
</figure>
<p class="Parallax__item__desc reveal reveal-TWO reveal-BTT"data-delay=1000>목표를 지닌 사람들만이 인생에서 진정으로 살아간다.</p>
</section>
<!-- //section9-->
</div>
</main>
<!-- main -->
<aside class="Parallax__info">
<div class="scroll">scrollTop : <span>0</span>px</div>
</aside>
<!-- Parallax__info -->
<footer id="footer">
<a href="mailto:ghkddn132@naver.com">ghkddn132@naver.com</a>
</footer>
<!-- footer -->
JAVASCRIPT
<script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.11.5/gsap.min.js"></script>
<script>
//p .reveal 자식요소에 span으로 감싸주세요!!
document.querySelectorAll("p.reveal").forEach(text => {
text.innerHTML = `<span>${text.innerHTML}</span>`
});
function scroll(){
let scrollTop = window.scrollY || window.pageYOffset;
const reveals = document.querySelectorAll(".reveal");
reveals.forEach(reveal => {
let revealOffset = reveal.offsetTop + reveal.parentElement.offsetTop; //parentElement는 부모
let revealDelay = reveal.dataset.delay;
// if(scrollTop >= revealOffset - window.innerHeight){
// reveal.classList.add("show")
// }
if(scrollTop >= revealOffset - window.innerHeight){
if(revealDelay == undefined){
reveal.classList.add("show")
} else {
setTimeout(() => {
reveal.classList.add("show");
}, revealDelay);
}
}
});
document.querySelector(".scroll span").innerText = Math.round(scrollTop);
requestAnimationFrame(scroll);
}
scroll();
</script>
※재귀 함수를 사용한 클래스에 스크롤값에 반응하여 값 넣기
<script src="https://cdnjs.cloudflare.com/ajax/libs/gsap/3.11.5/gsap.min.js"></script>
GSAP 라이브러리를 외부 스크립트로 가져옵니다. 이 라이브러리는 JavaScript 기반의 애니메이션 플러그인으로 많이 사용됩니다.
- 클래스가 "reveal"인 모든 <p> 요소를 선택합니다. 그런 다음, 선택된 각 요소에 대해 다음 코드를 실행합니다.
- text.innerHTML = <span>${text.innerHTML}</span>;: 선택된 요소의 내용을 변경하여 <span> 태그로 감싸줍니다.
- 스크롤 이벤트에 대한 처리를 담은 scroll 함수를 실행합니다.
- 현재 스크롤 위치를 scrollTop 변수에 저장합니다. window.scrollY는 모던 브라우저에서, window.pageYOffset는 브라우저에서 스크롤 위치를 가져오는 두 가지 방법을 모두 고려하여 값을 설정합니다.
- 클래스가 "reveal"인 모든 요소를 선택하여 reveals 변수에 저장합니다.
- eveals 요소 목록에 대해 반복문을 실행합니다. 각 요소에 대해 다음 코드를 실행합니다.
- reveal 요소의 상단 위치와 부모 요소의 상단 위치를 합산하여 revealOffset 변수에 저장합니다. 이렇게 함으로써 reveal 요소가 스크롤되었을 때 보여지는 영역을 정의합니다.
- reveal 요소의 data-delay 속성 값을 가져와 revealDelay 변수에 저장합니다. 이 속성은 애니메이션 지연 시간을 정의하는 데 사용됩니다.
- 현재 스크롤 위치가 reveal 요소가 화면에 보여지는 영역을 벗어나지 않는지 확인합니다.
- revealDelay 변수가 정의되지 않았는지 확인하여 애니메이션을 실행합니다. 정의되지 않았다면 즉시 애니메이션을 적용하고, 그렇지 않다면 setTimeout 함수를 사용하여 revealDelay 시간 이후에 애니메이션을 적용합니다.
- 애니메이션을 보여주기 위해 reveal 요소에 "show" 클래스를 추가합니다.
- HTML 문서에서 클래스가 "scroll"인 요소를 선택하고, 그 자식 요소인 <span>의 내용을 현재 스크롤 위치인 scrollTop 값으로 설정합니다.
- scroll 함수를 반복해서 실행하기 위해 requestAnimationFrame 메서드를 사용합니다. 이를 통해 애니메이션이 부드럽게 처리됩니다.
requestAnimationFrame | 브라우저에게 애니메이션을 수행하기 전에 다음 리페인트까지 애니메이션을 업데이트하고 그리도록 지시하는 메서드입니다. 이 메서드를 사용하면 브라우저의 리페인트 주기에 맞추어 애니메이션을 부드럽게 실행할 수 있습니다. |