javascript – Animated modal closing

Question:

var modal = document.getElementById('myModal');
var span = document.getElementsByClassName("close");
var buttons = document.getElementsByClassName("myBtn")

for (var i = 0; i < span.length; i++) {
  span[i].onclick = function() {
    var id = this.getAttribute('data-modal');
    var modal = document.getElementById(id);
    modal.style.display = 'none';
  }
}

for (var i = 0; i < buttons.length; i++) {
	buttons[i].onclick = function() {
    var id = this.getAttribute('data-modal');
    var modal = document.getElementById(id);
    modal.style.display = 'block';
  }
}

window.onclick = function(event) {
  var isModal = (' ' + event.target.className + ' ').indexOf(' modal ') > -1;
  if (isModal) {
    event.target.style.display = "none";
  }
}
.modal {
    display: none; /* Hidden by default */
    position: fixed; /* Stay in place */
    z-index: 100000; /* Sit on top */
    padding-top: 172px; /* Location of the box */
    left: 0;
    top: 0;
    width: 100%; /* Full width */
    height: 100%; /* Full height */
    overflow: auto; /* Enable scroll if needed */
    background-color: rgb(0,0,0); /* Fallback color */
    background-color: rgba(0,0,0,0.4); /* Black w/ opacity */
}

/* Modal Content */
.modal-content {
    position: relative;
    /* background-color: #fefefe; */
    margin: auto;
    padding: 0;
    /* border: 1px solid #888; */
    width: 684px;
    box-shadow: 0 4px 8px 0 rgba(0,0,0,0.2),0 6px 20px 0 rgba(0,0,0,0.19);
    -webkit-animation-name: animatetop;
    -webkit-animation-duration: 0.4s;
    animation-name: animatetop;
    animation-duration: 0.4s;
}

/* Add Animation */
@-webkit-keyframes animatetop {
    from {top:-300px; opacity:0} 
    to {top:0; opacity:1}
}

@keyframes animatetop {
    from {top:-300px; opacity:0}
    to {top:0; opacity:1}
}

/* The Close Button */
.close {
    margin-top: -11px;
    color: white;
    float: right;
    font-size: 28px;
    font-weight: bold;
}

.close:hover,
.close:focus {
    color: #000;
    text-decoration: none;
    cursor: pointer;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<button class="myBtn" data-modal="myModal1" >Open Modal</button>
<div id="myModal1" class="modal">
  <div class="modal-content">
    <div class="modal-header">
      <span class="close" data-modal="myModal1">&times;</span>
     
    </div>
    <div class="modal-body">
       text
    </div>
  </div>
</div>

There is a modal window, it opens with animation, and closes without it. How to implement that it also closes with animation? (Upwards).

Answer:

Such as:

$('.close').on('click', function(){
  var $this = $(this),
      modal = $this.closest('.modal'); 
  
  modal.toggleClass('show hide');
  
  setTimeout(function(){
    modal.removeClass('hide');
  }, 400);
});


$(".myBtn").on('click', function(e){
  e.preventDefault();  
  
  var $this = $(this),
      id = $this.data('modal'),
      modal = $('#'+id);
  
  if(!modal.hasClass('show')){
    modal.addClass('show');
   
  }else {
    modal.removeClass('show');
  }   
  
});


$(document).click(function (e) {
  var container = $('.modal');
  if ($(e.target).is('.modal')) {
    
    container.toggleClass('show hide');
  
    setTimeout(function(){
      container.removeClass('hide');
    }, 400);
  }
});
* {
  box-sizing: border-box;
}

.modal {
  display: none; 
  position: fixed; 
  z-index: 100000; 
  padding-top: 172px;
  left: 0;
  top: 0;
  width: 100%; 
  height: 100%; 
  overflow: auto; 
  padding: 1rem;
  background-color: rgb(0,0,0); 
  background-color: rgba(0,0,0,0.4);
}

.modal.show {
  display: block;
}

.modal-content {
  position: relative;
  background-color: #fefefe;
  margin: auto;
  padding: 0;
  max-width: 684px;
  width: 100%;
  box-shadow: 0 4px 8px 0 rgba(0,0,0,0.2),
    0 6px 20px 0 rgba(0,0,0,0.19); 
  
  transform: translateY(-300px);  opacity:0;
}



.modal.show .modal-content {
  animation: modalShow .4s both;
}

.modal.hide .modal-content {
  animation: modalHide .4s both;
}

.modal.hide {
  display: block;
}

@keyframes modalShow {
  /* from { transform: translateY(-300px);  opacity:0; } */
  to { transform: translateY(300px);  opacity:1; }
}


@keyframes modalHide {
  from { transform: translateY(300px);  opacity:1; }
  to { transform: translateY(-300px);  opacity:0; }
}

.close {
  font-size: 28px;
  font-weight: bold;
  
  cursor: pointer;
  position: absolute;
  right: 0;
  left: 100%;
  top: -14px;
  width: 14px;
  padding-right: 0;
  text-align: center;
  line-height: 28px;
  cursor: pointer !important;
  color: #fff;
}

.close:hover,
.close:focus {
  color: #000;
  text-decoration: none;
  cursor: pointer;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
  
<button class="myBtn" data-modal="myModal1" >Open Modal</button>
  
<div id="myModal1" class="modal">
  <div class="modal-content">
    <div class="modal-header">
      <span class="close">&times;</span>
     
    </div>
    <div class="modal-body">
       text
    </div>
  </div>
</div>

The point is that when you click on "close", another class must be added that is responsible for the animated closing.

If you just set dispaly: none , then everything instantly disappears along with the content.

Better yet, use a modal plugin like magnific popup that can be easily set up to animate on and off.

Scroll to Top