Search code examples
csscss-animationscss-transforms

CSS: Using transform translate instead of bottom


I am trying to change my keyframe animation for a button that moves something from the bottom of a div to the top. When I animate it using bottom:

@keyframes moveUpWithFade2 {
    from {
        bottom: 0%;
        opacity: 0;
    }
    10% {
        opacity: 1;  
    }
    50% {
        opacity: 1;
    }
    to {
        bottom: 100%;
        opacity: 0;
    }
}

it properly fades in from the bottom of the parent div to the very top. However, if I use transform: translateY(100%) it operates on the dimension of the div that I am trying to animate. So if I have a rectangle that has height 25px, then it will move up 25px. So in order to get the same behavior as bottom, I need to specify really high values of translateY, like so:

@keyframes moveUpWithFade {
    from {
        transform: translateY(0%);
        opacity: 0;
    }
    10% {
        transform:  translateY(-200%);
        opacity: 1;  
    }
    50% {
        transform:  translateY(-1000%);
        opacity: 1;
    }
    to {
        transform: translateY(-2000%);
        opacity: 0;
    }
}

JSFiddle link

.parent {
  width: 25px;
  height: 400px;
}

.rect {
  position: absolute;
  width: 25px;
  height: 25px;
  background-color: skyblue;
}

.movingDiv {    
    bottom: 0;
    animation: moveUpWithFade 6s linear infinite forwards, animateX 2s ease-in-out 3 alternate;
    overflow: hidden;
}

@keyframes moveUpWithFade {
    from {
        transform: translateY(0%);
        opacity: 0;
    }
    10% {
        transform:  translateY(-200%);
        opacity: 1;  
    }
    50% {
        transform:  translateY(-1000%);
        opacity: 1;
    }
    to {
        transform: translateY(-2000%);
        opacity: 0;
    }
}

@keyframes moveUpWithFade2 {
    from {
        bottom: 0%;
        opacity: 0;
    }
    10% {
        opacity: 1;  
    }
    50% {
        opacity: 1;
    }
    to {
        bottom: 100%;
        opacity: 0;
    }
}
<!-- Learn about this code on MDN: https://developer.mozilla.org/en-US/docs/Web/CSS/transform-function/translateY -->

<div class="parent">
<div class="rect movingDiv">Moving</div>
</div>

In my case the size of the object that I am moving up or down is variable and not hardcoded. Is there a way I could use transform property that operates on the height of the parent div to manipulate the child div?


Solution

  • Consider an extra element where you will apply the transform animation and make it the same height as the parent:

    .parent {
      width: 25px;
      height: 300px;
      border: 2px solid;
      overflow:hidden;
    }
    
    .rect {
      width: 25px;
      height: 25px;
      background-color: skyblue;
      transform:translateY(-100%);
    }
    
    .movingDiv {
      height:100%;
      animation: moveUpWithFade 6s linear infinite;
    }
    
    @keyframes moveUpWithFade {
      from {
        transform: translateY(100%);
        opacity: 0;
      }
      10% {
        transform: translateY(80%);
        opacity: 1;
      }
      50% {
        transform: translateY(30%);
        opacity: 1;
      }
      to {
        transform: translateY(0%);
        opacity: 0;
      }
    }
    <div class="parent">
      <div class="movingDiv">
        <div class="rect ">Moving</div>
      </div>
    </div>