0

I'm fiddling around with 3D CSS animations, and I've run into an issue where I have a moving element which is being translated on the X-axis. This transformation runs for 2 seconds. However, I also want to apply a rotation to the element on the Y-axis which runs for 30 seconds.

The problem I am running into is that since translate and rotate are both part of the transform property in CSS, there doesn't seem to be a way in which I can apply separate timings to each of them.

.ball {
  position: absolute;
  left: 50%;
  top: 50%;
  width: 50px;
  height: 50px;
  border-radius: 50%;
  background-color: red;
  animation: animate 2s infinite linear;
}

@keyframes animate {
  to {
    transform: translateX(100px) rotateY(360deg);
  }
}
<html>
  <body>
    <div class="ball"></div>
  </body>
</html>

As you can see, I'm able to make the ball both translate and rotate at the same time, but I cannot figure out how to apply separate timings to each animations. Again, I want the translation to be a 2 second animation, but the rotation I want to be a 30 second animation. Is this possible?

  • Multiple animations can be applied to a single element: https://developer.mozilla.org/en-US/docs/Web/CSS/animation#syntax – Sean Jun 04 '21 at 17:47
  • Thanks for responding so quickly. I think I did know that you could apply multiple animations to a single element. But CSS seems to treat both translate and rotate as subsets of the transform animation. Because of this, there doesn't seem to be a way to separate the two into different timings. – MasterBelac1 Jun 04 '21 at 17:56
  • Does this answer your question? [Play multiple CSS animations at the same time](https://stackoverflow.com/questions/26986129/play-multiple-css-animations-at-the-same-time) – Lakshya Thakur Jun 04 '21 at 17:57
  • Are you trying to slow one animation or, map one to the other ? because specifying two animations should do it – Rainbow Jun 04 '21 at 18:12

3 Answers3

1

As transform is a single property, you have to use a wrapper:

.ball {
    position: absolute;
    left: 50%;
    top: 50%;
    width: 50px;
    height: 50px;
    border-radius: 50%;
    background: linear-gradient(0deg, rgba(171,17,121,1) 0%,   rgba(17,171,154,1) 100%);
    animation: animate2 .5s infinite linear;
}

.ballWrapper {
    animation: animate 2s infinite linear;
}

@keyframes animate {
    to {
        transform: translateX(200px);
    }
}

@keyframes animate2 {
    to {
        transform: rotateY(360deg);
    }
}
<body>
    <div class="ballWrapper">
        <div class="ball"></div>
    </div>
</body>
Kevin M. Mansour
  • 2,915
  • 6
  • 18
  • 35
adrien
  • 32
  • 5
1

control the angle to increase the speed of the rotation or decrease it. I am using calc() to easily express the rotation as N*360deg but you can manually set the value you want

.ball {
  position: absolute;
  left: 50%;
  top: 50%;
  width: 50px;
  height: 50px;
  border-radius: 50%;
  background-color: red;
  animation: animate 2s infinite linear;
}

@keyframes animate {
  to {
    transform: translateX(100px) rotateY(calc(3*360deg));
  }
}
<html>
  <body>
    <div class="ball"></div>
  </body>
</html>
Temani Afif
  • 245,468
  • 26
  • 309
  • 415
0

While it would be possible to put all the animation into one animation that would be quite messy, and not very flexible as the %s would need working out again if either the 2 or 30 seconds were to change.

If you don't want to, or can't, alter the HTML you could have the translation applied to the div and the rotation to an after pseudo element.

.ball {
  position: absolute;
  left: 50%;
  top: 50%;
  width: 50px;
  height: 50px;
  animation: move 30s infinite linear;
}
.ball::after {
  content: '';
  position: absolute;
  top: 0;
  left: 0;
  width: 100%;
  height: 100%;
  border-radius: 50%;
  background-color: red;
  animation: animate 2s infinite linear;
  z-index: 1;
}

@keyframes animate {
  to {
    transform: rotateY(360deg);
  }
}
@keyframes move {
  to {
    transform: translateX(100px);
  }
}
<html>
  <body>
    <div class="ball"></div>
  </body>
</html>
A Haworth
  • 30,908
  • 4
  • 11
  • 14