0

I'm a little bit stuck on animations, so I have a div that is added dynamically using jQuery .append() so when the page is loaded the div content will be added and from css I'll apply some animations using @keyframes. My problem is when the div content is closed using jQuery .remove() because if the div content is removed how I will apply animation to this ? So basically on page loaded the content will animate from top to bottom and on close should go back from bottom to top, how can I do that reverse animation ? I want to apply that reverse animation using only css not js.

.child-container {
  background: red;
  height: 100px;
  width: 150px;
  padding: 10px;
  animation-name: anime;
  animation-duration: 1s;
}

@keyframes anime {
  from,
  0%,
  100%,
  to {
    animation-timing-function: cubic-bezier(0.25, 0.60, 0.35, 1.00);
  }
  0% {
    opacity: 0;
    transform: translate3d(0, -200px, 0);
  }
  100% {
    opacity: 1;
    transform: translate3d(0, 0, 0);
  }
}

$(document).ready(function() {
  $(".container").append($("<div class='child-container'>Hello Jimmy!<a class='close'><b>X</b></div>"));
  $(".close").on('click', function() {
    $(this).parent().remove();
  });
});
.container {
  padding: 10px;
  background: orange;
}

.child-container {
  background: red;
  height: 100px;
  width: 150px;
  padding: 10px;
  animation-name: anime;
  animation-duration: 1s;
}

.close {
  float: right;
  cursor: pointer;
}

.close:hover {
  color: #fff;
}


/*ANIMATIONS*/

@keyframes anime {
  from,
  0%,
  100%,
  to {
    animation-timing-function: cubic-bezier(0.25, 0.60, 0.35, 1.00);
  }
  0% {
    opacity: 0;
    transform: translate3d(0, -200px, 0);
  }
  100% {
    opacity: 1;
    transform: translate3d(0, 0, 0);
  }
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="container"></div>
CodeMonkey
  • 2,828
  • 1
  • 23
  • 32
mcmwhfy
  • 1,654
  • 5
  • 36
  • 58
  • you need to add a class by js for that, I don't think it can be done only by css because this need to be done on an event – sTx Mar 27 '17 at 07:17
  • You are looking for ONLY CSS based solution? You are already using JS in your fiddle. – Aslam Mar 27 '17 at 07:32
  • @ hunzaboy I know but on my project I'm not really able to do that, this is just an example ... – mcmwhfy Mar 27 '17 at 07:34
  • You can delay the removal so there is time for the reverse animation to run: http://stackoverflow.com/questions/3655627/jquery-append-object-remove-it-with-delay – Asons Mar 27 '17 at 10:35

3 Answers3

1

You must add a class to handle a new "state" of your element in css.

But you shouldn't use animation and keyframe for that. Instead, use transition. Exemple :

.myElement {
    top: 0;
    transition: top 0.4s linear;
}

.meElementOpened {
    top: 50%;
}

We set the transition on the element's default class (the one the element must always have) to handle the opening and the closing animation on the top property.

transition doc

Fahrenheit
  • 125
  • 5
  • can you create a fiddle with your idea ? but not using jQuery for adding class ... – mcmwhfy Mar 27 '17 at 07:29
  • 1
    you can't technically add a class with Css. Only thing you can handle would be a "hover", a "focus" or a "active"state. Il could create a fiddle using these states if you are still interested – Fahrenheit Mar 27 '17 at 08:01
  • I think the active state sound great, however I was thinking If I'll animate the container instead of child ? something like when the container will modify height to add some animations ? – mcmwhfy Mar 27 '17 at 08:10
  • It really depends on your html structure but it could be a good choice. The active state only trigger when you are clicking which mean that it will stop being triggered once you release the mouse click. – Fahrenheit Mar 27 '17 at 08:42
0

You don't need to use keyframes for this sort of animation. What you should rather do is toggle a class with changing top properties of your .child-container element and apply a transition.

Add the initial class with a setTimeout so that the class is applied and the animation happens. And remove the class on close. Note you can vary the transition timing here (I have provided a 1s duration here).

Updated fiddle.

Refer code:

$(document).ready(function() {
  $(".container").append($("<div class='child-container'>Hello Jimmy!<a class='close'><b>X</b></div>"));
  setTimeout(function() {
    $(".child-container").addClass("initial");
  }, 1);
  $(".close").on('click', function() {
    $(this).parent().removeClass("initial");
  });
});
.container {
  padding: 10px;
  background: orange;
}

.child-container {
  background: red;
  height: 100px;
  width: 150px;
  padding: 10px;
  top: -200px;
  position: relative;
  transition: all 1s;
}

.initial {
  top: 0;
}

.close {
  float: right;
  cursor: pointer;
}

.close:hover {
  color: #fff;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="container">

</div>
nashcheez
  • 5,067
  • 1
  • 27
  • 53
0

Bellow snippet will show the exact animation you have on open when closing the div.

$(document).ready(function() {
  $(".container").append($("<div class='child-container'>Hello Jimmy!<a class='close'><b>X</b></div>"));
  $(".close").on('click', function() {
    $(this).parent().css({
      "animation": "close-anime 1s forwards"
    });
  });
});
.container {
  padding: 10px;
  background: orange;
}

.child-container {
  background: red;
  height: 100px;
  width: 150px;
  padding: 10px;
  animation-name: anime;
  animation-duration: 1s;
}

.close {
  float: right;
  cursor: pointer;
}

.close:hover {
  color: #fff;
}


/*ANIMATIONS*/

@keyframes anime {
  from,
  0%,
  100%,
  to {
    animation-timing-function: cubic-bezier(0.25, 0.60, 0.35, 1.00);
  }
  0% {
    opacity: 0;
    transform: translate3d(0, -200px, 0);
  }
  100% {
    opacity: 1;
    transform: translate3d(0, 0, 0);
  }
}

@keyframes close-anime {
  from,
  0%,
  100%,
  to {
    animation-timing-function: cubic-bezier(0.25, 0.60, 0.35, 1.00);
  }
  0% {
    opacity: 0;
    transform: translate3d(0, 0, 0);
  }
  100% {
    opacity: 1;
    transform: translate3d(0, -200px, 0);
  }
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="container"></div>

added code:

CSS

@keyframes close-anime {
  from,
  0%,
  100%,
  to {
    animation-timing-function: cubic-bezier(0.25, 0.60, 0.35, 1.00);
  }
  0% {
    opacity: 0;
    transform: translate3d(0, 0, 0);
  }
  100% {
    opacity: 1;
    transform: translate3d(0, -200px, 0);
  }
}

JS

$(this).parent().css({
      "animation": "close-anime 1s forwards"
});
CodeMonkey
  • 2,828
  • 1
  • 23
  • 32