1. CSS 애니메이션
CSS 애니메이션은 JS 애니메이션에 비해 두 가지 주요 장점이 있습니다:
- 부드러움
렌더링 엔진이 프레임 스킵(frame-skipping) 및 기타 기술을 통해 성능을 최대한 부드럽게 보장할 수 있기 때문입니다.
- 브라우저 성능 최적화
애니메이션 시퀀스 제어를 브라우저에 맡김으로써 브라우저가 성능과 효율을 최적화할 수 있습니다. 예를 들어, 보이지 않는 탭의 경우 새로고침 빈도를 줄일 수 있습니다.
애니메이션 정의는 두 부분으로 나뉩니다:
-
animation의 다양한 하위 속성 설정 -
@keyframes를 통한 키프레임 스타일 정의
브라우저는 이러한 정보를 바탕으로 *트윈 애니메이션(tween animation)*을 생성하고, 보간(interpolation)을 계산하여 각 키프레임을 연결합니다.
2. animation 하위 속성
animation-name @keyframes에 정의된 키프레임 이름, 기본값 none
animation-duration 애니메이션 지속 시간, 기본값 0s, transition과 동일
animation-timing-function 이징(easing) 함수, 기본값 ease, transition과 동일
animation-delay 지연 시간, 기본값 0s, transition과 동일
animation-iteration-count 반복 횟수, 기본값 1
animation-direction 방향, 기본값 normal
animation-fill-mode 스타일 적용 모드, 기본값 none
animation-play-state 애니메이션 시퀀스 일시 중지/재개 제어, 기본값 running
주의 사항:
-
duration이delay보다 먼저 와야 하며, 나머지 매개변수 순서는 상관없습니다. -
animation-name은 예약어와 중복되지 않도록 하세요. 속성과 우선적으로 매칭됩니다.
animation-iteration-count
animation-iteration-count = infinite | <number>
애니메이션 반복 횟수이며, 각 값은 각각 무한, 지정된 횟수를 의미합니다.
animation-direction
animation-direction = normal | reverse | alternate | alternate-reverse
애니메이션 실행 방향이며, 각 값은 각각 정방향, 역방향, 교대(홀수 번째 정방향, 짝수 번째 역방향), 역방향 교대(홀수 번째 역방향, 짝수 번째 정방향)를 의미합니다.
animation-fill-mode
animation-fill-mode = none | forwards | backwards | both
스타일 적용 모드이며, 각 값은 각각 키프레임 스타일 미적용, (종료 후) 최종 상태 스타일 적용, (delay 기간 동안) 초기 상태 스타일 적용, (delay 기간 동안) 초기 상태 스타일 적용 및 (종료 후) 최종 상태 스타일 적용을 의미합니다.
주의: 초기 상태와 최종 상태는 0%일 수도 있고 100%일 수도 있으며, 이는 animation-iteration-count와 animation-direction에 의해 공동으로 결정됩니다.
키워드의 의미는 다음과 같습니다:
none 애니메이션 종료 후, @keyframes에 정의된 스타일을 제거하고 원래 스타일로 복구합니다.
forwards 애니메이션 종료 후, 최종 상태 스타일을 유지합니다.
backwards 애니메이션 시작 전(delay 기간 동안), 초기 상태 스타일을 유지합니다.
both forwards와 backwards 효과를 동시에 가집니다. 즉, delay 기간 동안 초기 상태 스타일을 유지하고 애니메이션 종료 후 최종 상태 스타일을 유지합니다.
구체적인 차이점은 데모를 참조하세요: http://www.ayqy.net/temp/animation/animation-fill-mode.html, 빨간색 블록을 클릭하면 애니메이션이 시작됩니다.
animation-play-state
animation-play-state = running | paused
애니메이션 실행 또는 일시 중지를 결정하며, 애니메이션의 일시 중지/재개를 제어하는 데 사용할 수 있습니다. delay보다 더 강력하고 유연합니다.
구체적인 효과는 데모를 참조하세요: http://www.ayqy.net/temp/animation/animation-play-state.html
3. @keyframes
구문은 다음과 같습니다:
@keyframes anmiationName {
0% {}
/*...*/
100% {}
}
0%와 100%가 정의되지 않은 경우, 브라우저는 다른 시점의 키프레임을 기반으로 모든 속성에 대한 값 세트를 계산합니다.
P.S. to와 from은 각각 0%와 100%의 별칭입니다. 초기 상태와 최종 상태가 중요하기 때문에 영어 이름을 가질 자격이 부여된 셈입니다.
4. 이벤트
transition에는 end 이벤트 하나만 있지만, animation은 세 가지 이벤트를 제공합니다:
animationstart 시작
animationend 종료
animationiteration 다음 반복 시작
이벤트 객체에는 세 가지 특수 속성이 있습니다:
-
animationName
즉
animation-name입니다. -
elapsedTime
단위는 초입니다.
animationstart및animationend의 경우 현재까지 애니메이션이 실행된 시간을 나타내며,animationiteration의 경우 다음 반복이 시작되는 시간을 나타냅니다.transitionend이벤트와 유사하며 일반적으로 delay의 영향을 받지 않습니다.특별히,
animationstart의elapsedTime은 일반적으로0이지만,animation-delay가 음수일 경우elapsedTime은-1 * delay가 됩니다. -
pseudoElement
::로 시작하는 가상 요소 이름입니다. 애니메이션이 가상 요소에 적용되지 않은 경우 빈 문자열입니다.
주의: 마지막 반복이 끝날 때는 animationiteration이 트리거되지 않고 animationend가 트리거됩니다.
5. 팁
1. steps(1)을 사용하여 부드러운 전환 제거
steps(1)은 linear와 매우 비슷합니다. linear 애니메이션의 트윈 전환을 제거하고 키프레임만 남기며, 키프레임 사이의 프레임이 이전 키프레임을 유지하도록 하면 steps(1)이 됩니다.
Flash를 제작할 때 먼저 두 개의 키프레임을 삽입하면, 두 키프레임 사이는 모두 일반 프레임(이전 키프레임의 재생 시간을 연장하는 데 사용됨)이 되며, 이때의 효과가 steps(1)입니다. 뒤쪽 키프레임을 우클릭하여 트윈 애니메이션을 생성하면 linear 효과를 얻을 수 있습니다.
실제 예시는 다음과 같습니다:
.rgb {
-webkit-animation: rgb 1.5s linear infinite;
animation: rgb 1.5s linear infinite;
}
@keyframes rgb {
0% {
opacity: red;
}
33% {
background: green;
}
66% {
background: blue;
}
}
효과는 배경색이 빨강, 초록, 파랑으로 부드럽게 변하는 것입니다. 그라데이션의 부드러운 전환을 제거하려면 다음과 같이 linear를 steps(1)로 변경하면 됩니다:
.rgb-step {
-webkit-animation: rgb 1.5s steps(1) infinite;
animation: rgb 1.5s steps(1) infinite;
}
효과는 0.5초마다 배경색이 전환되며 그라데이션 전환이 없는 상태가 됩니다.
구체적인 응용: 두 가지 상태 무한 전환 (깜빡임)
.blink {
-webkit-animation: blink 1s steps(1) infinite;
animation: blink 1s steps(1) infinite;
}
@keyframes blink {
0% {
opacity: 0;
}
50% {
opacity: 1;
}
}
2. 키프레임을 추가하여 부드러운 전환 제거
깜빡임 효과를 구현하는 또 다른 흥미로운 방법이 있습니다:
.blink {
-webkit-animation: blink 1s linear infinite;
animation: blink 1s linear infinite;
}
@keyframes blink {
0% {
opacity: 0;
}
50% {
opacity: 0;
}
50.01% {
opacity: 1;
}
100% {
opacity: 1;
}
}
여전히 linear 부드러운 전환이지만, 삽입된:
50.01% {
opacity: 1;
}
부분이 50% -> 100% 사이의 트윈을 제거하고 투명도 트윈을 50% -> 50.01%로 옮깁니다. 시간이 짧은 경우 이 트윈 변화는 감지되지 않습니다. 물론 시간이 충분히 길다면, 예를 들어:
.blink {
-webkit-animation: blink 10000s linear infinite;
animation: blink 10000s linear infinite;
}
특정 1초 동안 투명도가 0에서 1로 변하는 것을 볼 수 있겠지만, 일반적인 경우 이렇게 깜빡임을 구현해도 효과상 문제는 없습니다.
3. 키프레임을 이용한 지연 제어
animation-delay는 애니메이션 시작 전에만 유효하며, 반복될 때마다 지연이 삽입되지 않습니다. 위의 50.01% 기법과 유사하게, 빈 키프레임을 삽입하여 매 반복마다 지연을 추가함으로써 로딩 애니메이션이 한 바퀴 돌고 멈췄다 다시 도는 효과를 구현할 수 있습니다:
.wait {
-webkit-animation: wait 1s linear infinite;
animation: wait 1s linear infinite;
}
@keyframes wait {
0% {
-webkit-transform: rotateZ(0);
transform: rotateZ(0);
}
40% {
-webkit-transform: rotateZ(0);
transform: rotateZ(0);
}
100% {
-webkit-transform: rotateZ(360deg);
transform: rotateZ(360deg);
}
}
한 바퀴 돌 때마다 0.4s씩 기다리게 됩니다.
4. steps를 이용한 프레임 애니메이션
프레임 시퀀스를 하나의 이미지에 나열하고 background-position을 수정합니다.
steps()를 사용하여 구현할 경우 끝에 첫 번째 프레임을 복사해야 합니다(예: 6프레임 애니메이션의 경우 7프레임이 나열된 이미지가 필요함). 예시는 다음과 같습니다:
.walk {
background: url(walk.svg);
width: 162px;
height: 230px;
-webkit-animation: walk 1s steps(22) infinite;
animation: walk 1s steps(22) infinite;
}
@keyframes walk {
0% {
background-position: 0 0;
}
100% {
background-position: -3564px 0;
}
}
여기서 walk.svg는 가로로 23프레임이 채워져 있으며, 각 프레임 크기는 162 * 230입니다. 배경 이미지를 왼쪽으로 당기면 최대 162 * 22 = 3564까지 당길 수 있으며, 이때 마지막 프레임(첫 번째 프레임과 내용이 동일함)이 표시되어 처음과 끝이 연결됩니다.
물론 steps(1)로 부드러운 전환을 제거한 후 22개의 키프레임을 수동으로 설정하는 또 다른 방법도 있습니다. 다소 번거롭기 때문에 여기서는 예시를 생략하지만, 분명히 가능한 방법입니다.
온라인 데모: http://www.ayqy.net/temp/animation/css-animation-tricks.html
6. 결론
CSS 애니메이션의 정의 방식은 Flash와 매우 유사합니다. 예를 들어 Flash의 몇 가지 개념을 살펴보면:
-
키프레임: 특정 부분의 내용이 이전과 다르기를 원한다면 키프레임을 삽입합니다.
-
빈 키프레임: 내용이 없음을 나타내며 하얀색 점으로 표시됩니다. 키프레임과 서로 전환될 수 있으며, 내용을 넣으면 키프레임이 되고 키프레임의 내용을 지우면 빈 키프레임이 됩니다.
-
일반 프레임: 키프레임이나 빈 키프레임 뒤에 이어지는 프레임입니다. 일반 프레임은 이전 키프레임의 내용을 유지하므로 애니메이션의 표시 시간을 제어하는 역할을 합니다.
CSS의 @keyframes 정의에 대입해서 생각해보면 꽤 흥미롭지 않나요?
아직 댓글이 없습니다