UI 디자인 애니메이션 연구소

커서 애니메이션 | 누구나 쉽게 따라하는 마우스 움직임에 따라 연기 효과 만들기 (Vanilla JS + CSS)

정보덕 2025. 6. 2. 10:16
반응형

반갑습니다.  아주 오랜만에 찾아 뵙게 되었습니다. 

 

오늘은 순수 JavaScript와 CSS만으로 마우스를 따라다니는 연기(smoke) 효과를 만들어보는 방법을 소개해드리겠습니다. 마우스를 움직이면 흩날리는 연기처럼 보이는 원들이 생성되고, 자연스럽게 사라지는 애니메이션 효과가 적용됩니다.

아주 간단한 코드지만 시각적으로 꽤 멋진 효과를 줄 수 있어요!

 

최종 결과 미리 보기

마우스를 움직이면 연기 같은 둥근 원이 생기고 서서히 커지면서 위로 날아가듯 사라지는 효과가 구현됩니다.

 

HTML 구조

먼저 HTML은 아주 간단합니다.

애니메이션 원들이 추가될 컨테이너 역할의 <div class="smoke"> 하나만 있으면 됩니다.

<div class="smoke"></div>

 

CSS 스타일링

연기 효과의 핵심은 CSS 애니메이션입니다. circle 클래스에 원형 모양을 주고, 커지면서 투명해지는 @keyframes 애니메이션을 적용합니다.

body {
  background: black;
}

.smoke {
  position: fixed;
  left: 0;
  top: 0;
  width: 100%;
  height: 100vh;
}

.circle {
  position: absolute;
  width: 10px;
  height: 10px;
  border-radius: 50%;
  background: radial-gradient(circle, rgba(255,255,255,0.8) 0%, rgba(255,255,255,0.5) 20%, rgba(255,255,255,0.1) 50%);
  animation: 1s sizeup ease-out forwards;
}

@keyframes sizeup {
  0% {
    scale: 0;
    transform: translateY(0);
  }
  100% {
    scale: 15;
    opacity: 0;
    transform: translateY(-10px);
  }
}

 

- radial-gradient를 사용해서 중심이 밝고 바깥으로 퍼지는 느낌을 줍니다.

- scale: 15로 커지게 하고 opacity: 0으로 점점 사라지는 효과를 줬습니다.

- translateY(-10px)은 살짝 위로 올라가는 연기 느낌을 주기 위한 트릭입니다.

 

JavaScript로 효과 제어하기

이제 마우스가 움직일 때마다 연기 원을 생성해주는 자바스크립트를 작성해봅니다.

const smoke = document.querySelector(".smoke");

function createSmokeEffect(e) {
  const circle = document.createElement("div");
  circle.classList.add("circle");

  circle.style.left = `${e.clientX}px`;
  circle.style.top = `${e.clientY}px`;

  smoke.appendChild(circle);

  // 연기 효과가 끝난 뒤 DOM에서 제거
  removeCircleElementVer2(circle);
}

연기가 너무 많이 생기지 않도록, 애니메이션이 끝난 뒤 자동으로 요소를 제거해주는 함수도 추가합니다. 방법에는 두 가지가 있는데, 각각 살펴보도록 합시다.

 

방법 1: setTimeout (비추천)

setTimeout은 애니메이션 시간과 딱 맞춰야 하고, 메모리에 타이머가 남기 때문에 추천하지 않습니다.

function removeCircleElementVer1(circle) {
  let timeId = setTimeout(() => {
    smoke.removeChild(circle);
  }, 1000);
}

 

방법 2: animationend 이벤트 리스너 (권장)

애니메이션이 진짜 끝난 시점에 요소를 제거하기 때문에 더 정확하고 안정적입니다.

function removeCircleElementVer2(circle) {
  circle.addEventListener("animationend", () => {
    circle.remove();
  });
}

 

이벤트 등록

마지막으로 마우스가 움직일 때 createSmokeEffect 함수가 호출되도록 이벤트를 등록합니다.

window.addEventListener("mousemove", createSmokeEffect);

 

마무리

See the Pen 연기 커서 by youngwan2 (@youngwan2) on CodePen.

 

이렇게 마우스 움직임에 따라 연기 효과를 만드는 간단한 인터랙션을 구현해보았습니다.

기본적인 원리만 이해하고 나면 색상, 크기, 애니메이션 시간 등을 바꿔서 불꽃, 물방울, 마법 이펙트 등 다양한 형태로 응용도 가능합니다!

필요하다면 requestAnimationFrame이나 throttle 기법을 추가해서 성능 개선도 가능하니 참고해주세요.

 

그럼 오늘도 즐코딩 하세요!

 

반응형