Reputation: 23
I'm a new learner and I don't have enough knowledge about animations. I have tried to implement a simple animation using keyframes and hover effect. The problem is if I hover the element when the animation is not finished yet, it instantly shows the hovered state without any transition right after the animation. You can try it below to see what I mean. How to fix that instant change?
@keyframes appear {
0% {
opacity: 0;
transform: translate(-50%, -50%) scale(0);
}
50% {
opacity: 1;
transform: translate(-50%, -50%) scale(1);
}
100% {
opacity: 1;
transform: translate(-50%, -50%) scale(0);
}
}
.element {
position: relative;
width: 200px;
height: 200px;
background-color: #ccc;
}
.element::after {
position: absolute;
content: "";
width: 80%;
height: 80%;
top: 50%;
left: 50%;
transform-origin: center;
background-color: crimson;
transform: translate(-50%, -50%) scale(0);
border-radius: 50%;
animation: appear 2s ease-in-out;
transition: all 1s ease-in-out;
}
.element:hover::after {
transform: translate(-50%, -50%) scale(0.8);
}
<div class="element"></div>
I have tried forward
to maintain the end keyframe but that prevents the hover effect from happening I guess.
Then I accidentally found using 0%
and 50%
keyframes only (or any keyframe less then 100%
so animation is not finished). It plays the animation for the first half of duration and then apply transition between the end keyframe and the hover state state of the element. Why this one works? Is it okay to use those incomplete keyframes? Is that a common solution? This solution also has some kind of bugs I guess but not as big as the first snippet.
@keyframes appear {
0% {
opacity: 0;
transform: translate(-50%, -50%) scale(0);
}
25% {
opacity: 1;
transform: translate(-50%, -50%) scale(1);
}
50% {
opacity: 0;
transform: translate(-50%, -50%) scale(0);
}
}
.element {
position: relative;
width: 200px;
height: 200px;
background-color: #ccc;
}
.element::after {
position: absolute;
content: "";
width: 80%;
height: 80%;
top: 50%;
left: 50%;
transform-origin: center;
background-color: crimson;
transform: translate(-50%, -50%) scale(0);
border-radius: 50%;
animation: appear 4s ease-in-out;
transition: all 1s ease-in-out;
}
.element:hover::after {
transform: translate(-50%, -50%) scale(0.8);
}
<div class="element"></div>
What's the best (or most common) way to handle this problem?
The first code snippet causes the hover effect to end abruptly if the element is hovered while its initial appearance animation is still playing.
The second code snippet improves this by using 50%
as the keyframe stop, which helps smooth the transition. However, I'm not sure whether using 50%
in this way is a common practice or if there's a better way to ensure the hover transition works seamlessly after the animation completes.
TL;DR How can I make hover transitions take effect only after the animation finishes, instead of applying the hover effect while the appear animation is still playing? (Without JavaScript if possible)
Upvotes: 1
Views: 55