【问题标题】:CSS Transition from display none to display block and vice versaCSS 从无显示过渡到显示块,反之亦然
【发布时间】:2017-07-13 20:44:49
【问题描述】:

我知道这个问题在 SO 中可能已经被问过数百万次了,但我已经尝试了大部分解决方案,我只是不知道为什么它对我不起作用。

所以我有一个带有display 的下拉菜单,最初针对none。当我点击它时,它显示出很好的过渡。 (到目前为止,一切都很好)。但是当我再次单击它以隐藏下拉列表时,它会立即隐藏,但我不希望那样。我想隐藏分配给显示的类似过渡。这是我的 CSS 代码:

.dropdown-menu {
  padding: 0 0;
  display: none;
  -webkit-animation: slide-down .3s ease-out;
  -moz-animation: slide-down .3s ease-out;
}

.table-dropdown-open {
  display: block;
  -webkit-animation: slide-down .3s ease-out;
  -moz-animation: slide-down .3s ease-out;
}

@-webkit-keyframes slide-down {
  0% {
    opacity: 0;
    -webkit-transform: translateY(-10%);
  }
  100% {
    opacity: 1;
    -webkit-transform: translateY(0);
  }
}

@-moz-keyframes slide-down {
  0% {
    opacity: 0;
    -moz-transform: translateY(-10%);
  }
  100% {
    opacity: 1;
    -moz-transform: translateY(0);
  }
}

这不是重复的,因为我试图从 block 过渡到 none。不是从noneblock

【问题讨论】:

  • CSS 中的过渡或动画在 display: none / display: block 上不起作用。使用 opacity: 0 / opacity: 1visibility 属性。
  • 我认为它会起作用,因为您可以从块集成到无。你确定它不会从无到阻止吗? @MuhammadUsman
  • @DingDong 你能举个例子,display 属性逐渐从block 过渡到none,好吗?我从没想过这是可能的。非常感谢您的努力,谢谢。
  • display 它始终和 transition animatable 财产。比如opacity,从01。你也可以玩transform。实际上,transformopacity 是仅有的 2 个您应该设置动画的属性,因为它们不需要 DOM 重新绘制除您正在设置动画的元素之外的任何内容,因此不会影响浏览器性能,即使您'同时为大量元素制作动画。

标签: html css drop-down-menu css-transitions css-animations


【解决方案1】:

display 始终是您的元素,并且只有 transition 任何 animatable 属性。在您的情况下,opacity 看起来是一个不错的候选人,尽管使用 transform 也可能会给您带来想要的结果。简单示例:

any {
  transform: scale(0);
  transition: transform .4s cubic-bezier(.5,0,.3,1);
}
any.animated {
  transform: scale(1);
}

实际上,opacitytransform 应该是您应该设置动画的仅有的两个属性,因为它们不需要 DOM 在动画元素以外的任何内容上重绘,因此不会影响浏览器性能,即使您'同时为大量元素制作动画。

请注意,即使没有绘制,您的元素实际上也处于完全没有transformed 时的位置。因此,您可能希望在它们处于 "invisible" 状态时给它们 pointer-events:none,而在它们处于 "visible" 状态时给它们 pointer-events:all,所以它们不会t 在不可见时捕获任何指针事件。


考虑到您的示例,我为您提供了两个动画示例(有关键帧和没有关键帧)。请记住,您需要prefix your code。为了完全兼容浏览器,请在设置中使用> 0%(底部的小框)。

setTimeout(function(){
  var dm = document.querySelector('.dropdown-menu');
  dm.classList.remove('hide-menu');
}, 300);
/* simple animation example, on parent. No keyframes. */
.dropdown-menu.hide-menu {
  opacity: 0;
}
.dropdown-menu {
  opacity: 1;
  transition: opacity .2s cubic-bezier(.4,0,.2,1);
  position: relative;
  animation: delay-overflow .3s;
  animation-fill-mode: forwards;
  animation-iteration-count: 1;
}
.dropdown-menu:hover {
  animation: none;
  cursor: pointer;
}

/* animation example with keyframes, on child */

.dropdown-menu ul {
  position: absolute;
  margin-top: 0;
  padding-top: 1rem;
  top: 100%;
  opacity: 0;
  transform: translateY(-10%);
  animation: slide-up .3s;
  animation-fill-mode: forwards;
  animation-iteration-count: 1;
}

.drowdown-menu.hide-menu ul {
  animation-duration: 0s;
}
.dropdown-menu:hover ul {
  animation: slide-down .3s;
  animation-fill-mode: forwards;
}


@keyframes slide-down {
  from {
    opacity: 0;
    transform: translateY(-10%);
  }
  to {
    opacity: 1;
    transform: translateY(0);
  }
}

@keyframes slide-up {
  from {
    opacity: 1;
    transform: translateY(0);
  }
  to {
    opacity: 0;
    transform: translateY(-10%);
  }
}
@keyframes delay-overflow {
  0% {
    overflow: visible;
  }
  99% {
    overflow: visible;
  }
  100% {
    overflow: hidden;
  }
}
<div class="dropdown-menu hide-menu">
  <span>Menu</span>
  <ul>
    <li>A menu item</li>
    <li>Another menu item</li>
    <li>...</li>
    <li>And so on...</li>
  </ul>
</div>

注意:animation 属性的一个非常方便的技巧是,它允许您延迟应用任何属性,即使是不可动画的属性也可以延迟应用所需的时间。我正在使用这个技巧来延迟overflow:hidden 在父级上的应用(并且overflow 是不可动画的),因此子级的动画(发生在父级边界之外)直到最后都是可见的。完成后,overflow:hidden 应用,它不再捕获菜单打开器之外的鼠标事件。

【讨论】:

  • 如果您对有关浏览器性能的动画和在元素集合上触发交错动画感兴趣,我最近回答了another question 并提供了有关该主题的更多详细信息。
【解决方案2】:

这只是一个简单的逻辑,您当前已经设置了向下滑动的样式,但您还没有设置取消 div 的样式。你必须首先有一个关闭状态,我相信你的情况是 .dropdown-menu

.dropdown-menu {
    transition: all 500ms ease;
}

或者直接使用

.dropdown-menu {
    transition: margin 300ms cubic-bezier(0.17, 0.04, 0.03, 0.94);
}

如果这不起作用,

【讨论】:

    猜你喜欢
    • 2016-12-10
    • 1970-01-01
    • 2012-11-20
    • 1970-01-01
    • 2017-07-20
    • 1970-01-01
    • 2018-01-16
    • 2014-04-26
    • 1970-01-01
    相关资源
    最近更新 更多