처음 개발을 접하게 되면 일반적으로 기능 중심이 구현이 되기 마련입니다.
너무도 당연한 말이겠지만 기능 중심으로 개발을 하다보면 결과물이 내 노력만큼 만족스럽지 못할 때가 종종 있습니다. 그럴때 아주 간단한 방법으로 결과물을 퀄리티를 높일 수 있는 방법이 있는데,
저는 그중에도 fade-effect를 꼽고 싶습니다.
개인적으로 깔끔하고 직관적인 페이지의 예시라고 생각합니다.
랜딩페이지는 각각의 기능을 가진 아이콘들이 모이고 스크롤을 통해 동적인 반응을 사용자에게 전해주고 있습니다.
이렇듯 fade-effect를 활용하면 고급진 페이지를 만들 수 있습니다.
이번 포스트에서는 3가지 방법에 대해 살펴보겠습니다.
제가 찾아본 방법중 가장 고전적이고 예제가 많이 있던 방법입니다.
jquery로 스크롤의 위치를 찾고 해당 위치에 따라 각 엘리먼트의 투명도, 슬라이딩 값을 지정해주고 css로 스타일을 변경해주는 방법입니다.
#장점
고전적인 방법인 만큼 다양하고 많은 예제가 있음.
#단점
고전적인 방법인 만큼 jquery를 쓰고, fade 효과를 주고자 하는 모든 엘리먼트에 대해 연산이 들어감으로 오버헤드가 강하게 발생합니다.
$(window).on("load", function () {
function fade() {
let animation_height = $(window).innerHeight() * 0.5;
let ratio = Math.round((1 / animation_height) * 10000) / 10000;
$(".fade").each(function () {
let objectTop = $(this).offset().top;
let windowBottom = $(window).scrollTop() + $(window).innerHeight();
if (objectTop < windowBottom) {
if (objectTop < windowBottom - animation_height) {
$(this).css({
transition: "opacity 0.1s linear",
transition: "left 0.1s linear",
opacity: 1,
left: "0px",
});
} else {
$(this).css({
transition: "opacity 0.5s linear",
opacity: (windowBottom - objectTop) * ratio,
transition: "left 0.5s linear",
left: `${200 * (1 - (windowBottom - objectTop) * ratio)}px`,
});
}
} else {
$(this).css({
opacity: 0,
left: "200px",
});
}
});
}
$(".fade").css({
opacity: 0,
left: "200px",
});
fade();
$(window).scroll(function () {
fade();
});
});
.fade {
position: relative;
}
<section class="fade" id="intro">
</section>
제가 찾아본 방법중 가장 쉽고 간편한 방법입니다.
대중적인 오픈소스인 만큼 fade effect뿐만 아니라 다양한 effect(Flip, Slide, Zoom, Anchor, Easing)들이 있습니다.
또한 readme에 구현방법부터 각 옵션이 잘 정리되어 있으니 읽고 따라하면 되는 방법입니다.
#장점
압도적인 편의성, 기능성
#단점
아직 못찾았음.
대부분의 기능들을 이미 나와있는 경우가 많고, 다 준비되어 있습니다.
다만 가장 큰 문제는, 내가 모른다는 사실입니다.
즉, 현재 화면에 표시되는 엘리먼트들을 찾아와서 무언 갈 할 수 있도록 제공해준다는 말입니다.
따라서 이 함수를 통해 추적하고자 하는 엘리먼트를 찾아 observer에 등록하고 해당 엘리먼트가 viewport안에 들어왔을때 하고자 하는 동작을 정의해줍니다. 그러면 해당 엘리먼트가 원하는 동작를 수행합니다.(viewport 안에 들어왔을 때요)
const targets = document.querySelectorAll(".fade-class");
const options = { root: null, threshold: 0.1, rootMargin: "-0px" };
const observer = new IntersectionObserver(function (entries, observer) {
entries.forEach((entry) => {
const container = entry.target;
if (entry.isIntersecting) {
container.classList.add("fade-in");
} else {
container.classList.remove("fade-in");
}
});
}, options);
targets.forEach((target) => {
observer.observe(target);
});
.fade-class {
position: relative;
left: 200px;
opacity: 0;
transition: left 0.5s cubic-bezier(0.4, 0, 0.2, 1), opacity 0.5s linear;
}
.fade-in {
transition: left 0.5s cubic-bezier(0.4, 0, 0.2, 1), opacity 0.5s linear;
left: 0px;
opacity: 1;
}
<section class="fade-class" id="intro">
</section>
이렇게 3가지 방법으로 구현을 해보았습니다.
개인적으로 편한 순위를 꼽는다면 아래와 같습니다.
그러니 간단한 시각적 효과가 필요할 때는 라이브러리를 사용하여 구현하는 것을 추천하고,
시각적 효과뿐만 아니라 추가적인 기능일 더 필요하다면 intersection observer를 추천합니다.
jquery는 그냥 쓰지 마세요.
여러분들의 fade effect 구현 방법은 어떻게 되시나요? 여러분들의 노하우도 댓글로 공유주시면 감사드리겠습니다.