브라우저의 재발견 · 마이크로 인터랙션

클릭 한 번에 담긴 0.5초의 디테일

버튼·폼·알림이 손끝에 반응하는 작은 움직임 9가지. 앱이 ‘살아있다’고 느끼게 하는 건 큰 연출이 아니라 이 마이크로 인터랙션이다. 공통 비밀은 오버슈트 스프링 곡선 cubic-bezier(.34,1.56,.64,1) — 목표를 살짝 지나쳤다 돌아온다.

↻ 자동 재생 + 직접 클릭해도 반응합니다.

01스프링 토글toggle switch
cubic-bezier(.34,1.56,.64,1) 오버슈트

스프링 토글 스위치

필요한 것

노브가 살짝 지나쳤다 돌아오는 스프링 이징이 핵심. 밋밋한 ease와 손맛 차이가 크다. 상태 색 전환도 함께.

AI에게 이렇게

“iOS처럼 통통 튀는 스프링 느낌의 토글 스위치 만들어줘. 오버슈트 이징으로.”

핵심 코드
transition:transform .5s cubic-bezier(.34,1.56,.64,1); .on i{transform:translateX(40px)}
02좋아요 버스트like burst
파티클 6~8개 방사 + 하트 스케일 팝

좋아요 파티클 버스트

필요한 것

하트가 스프링으로 팽창하며 색 점 6~8개가 사방으로 튄다. 점마다 CSS 변수(--dx,--dy)로 방향만 다르게 주면 keyframes 하나로 끝.

AI에게 이렇게

“트위터 좋아요처럼 하트 누르면 색 파티클이 사방으로 터지는 버스트 효과 만들어줘.”

핵심 코드
.p{--dx:34px;--dy:-26px;animation:burst .65s forwards} @keyframes burst{to{transform: translate(var(--dx),var(--dy)) scale(.4);opacity:0}}
03리플 (물결)ripple
클릭 좌표에 원 생성 → scale 확산

머티리얼 리플

필요한 것

클릭한 지점에 반투명 원을 만들어 커지며 사라지게 한다. 구글 머티리얼 디자인의 시그니처. 좌표는 e.offsetX/Y.

AI에게 이렇게

“버튼 클릭한 위치에서 물결이 퍼지는 머티리얼 리플 효과 넣어줘.”

핵심 코드
const i=document.createElement("i"); i.style.left=e.offsetX+"px";i.style.top=e.offsetY+"px"; btn.appendChild(i); // scale(0)→scale(1)+fade
04플로팅 라벨floating label
:focus → 라벨 translateY+scale(.72)

플로팅 라벨 입력창

필요한 것

포커스되면 플레이스홀더가 위로 떠올라 라벨이 된다. 자리 절약 + 맥락 유지. :focus와 ‘값 있음’ 상태 둘 다에 적용해야 한다.

AI에게 이렇게

“입력창 포커스하면 플레이스홀더가 위로 떠올라 작은 라벨이 되는 플로팅 라벨 만들어줘.”

핵심 코드
input:focus + label, input:not(:placeholder-shown) + label{ transform:translateY(-8px) scale(.72)}
05별점 채우기star rating
순차 채움 i×90ms + 스케일 팝

별점 순차 채우기

필요한 것

선택한 별까지 왼쪽부터 시차를 두고 노랗게 팝. 채워질 때 살짝 커졌다 돌아오면(스프링) 손맛이 산다.

AI에게 이렇게

“별점 클릭하면 그 별까지 순서대로 통통 튀며 노랗게 채워지게 해줘.”

핵심 코드
stars.forEach((s,i)=>setTimeout(()=> s.classList.toggle("on", i<=picked), i*90));
06체크 드로우checkbox draw
stroke-dashoffset 26 → 0 (선 그리기)

체크박스 선 그리기

필요한 것

체크 표시가 펜으로 긋듯 그려진다. SVG 선 길이만큼 dasharray를 주고 offset을 0으로. 상자 팝(scale)과 함께.

AI에게 이렇게

“체크박스 선택하면 체크 표시가 손으로 긋는 것처럼 그려지게 해줘. stroke-dashoffset으로.”

핵심 코드
polyline{stroke-dasharray:26;stroke-dashoffset:26} .on polyline{stroke-dashoffset:0;transition:.38s}
07스프링 스쿼시squash · stretch
scale(.9,.82) → (1.06,1.1) → 1

스쿼시 & 스트레치 버튼

필요한 것

디즈니 애니메이션 12원칙의 squash & stretch. 눌리면 납작해졌다(가로↑세로↓) 튀어오르며 원상복귀. 가로세로를 따로 스케일하는 게 포인트.

AI에게 이렇게

“버튼 누르면 젤리처럼 납작해졌다가 튀어오르는 스쿼시 앤 스트레치 효과 넣어줘.”

핵심 코드
@keyframes squish{35%{transform:scale(.9,.82)} 70%{transform:scale(1.06,1.1)}}
08알림 벨 + 배지bell ring · badge
3
rotate 감쇠 진동 + 배지 스프링 팝

알림 벨 흔들림 + 배지 팝

필요한 것

벨이 위쪽 고정점 기준으로 점점 작아지는 진폭으로 흔들리고(감쇠 진동), 빨간 배지가 스프링으로 튀어나온다. transform-origin이 핵심.

AI에게 이렇게

“새 알림 오면 종이 딸랑딸랑 흔들리고 빨간 숫자 배지가 통 튀어나오게 해줘.”

핵심 코드
svg{transform-origin:top center} @keyframes ring{15%{rotate:22deg}30%{rotate:-18deg} 45%{rotate:12deg}60%{rotate:-8deg}}
09카피 피드백copy feedback
아이콘 몰프 복사 → ✓ 복사됨

카피 버튼 상태 피드백

필요한 것

누르면 아이콘이 체크로 몰프되고 문구가 ‘복사됨!’으로 2초간 바뀌었다 복귀. ‘동작이 성공했다’는 확신을 주는 최소 비용의 피드백.

AI에게 이렇게

“복사 버튼 누르면 클립보드에 복사되고 아이콘이 체크로 바뀌며 ‘복사됨!’ 표시 후 원래대로 돌아오게 해줘.”

핵심 코드
await navigator.clipboard.writeText(code); btn.classList.add("on"); txt.textContent="복사됨!"; setTimeout(()=>{ /* 복귀 */ }, 2000);