I've 回答了一个问题 https://stackoverflow.com/a/43372990/3162554关于如何在悬停子元素时启动动画,然后保留应用的样式,直到取消悬停父元素。然而,我在我提出的解决方案中发现了一个我无法解释但我想理解的行为。阅读相关部分规格 https://www.w3.org/TR/css3-transitions/没有帮助我。
这是一个显示预期行为的最小示例。它可以工作,但由于某些原因,后面带有注释的属性必须有所不同。否则(例如,两者的值都是 10px),父级的取消悬停不会对子级的宽度产生任何影响。JSFiddle https://jsfiddle.net/4fc493ge/.
.parent {
border: 1px solid orange;
padding: 20px;
width: 400px;
}
.parent .child {
display: inline-block;
height: 40px;
background: blue;
transition: width 0.5s ease 600s;
width: 10px; /* why does this value has to be different ... */
/* Hint:
If you hover the child until it reaches the 100px, then hover the
parent without leaving the parent and keeping that hover for the
transition-delay (600s) the width will become 10px as defined here.
And removing this width property here won't make the transition work
at all. */
}
.parent .child:hover {
transition-delay: 0s;
width: 100px;
}
.parent:not(:hover) .child {
transition: width 0.5s ease 0s;
width: 11px; /* ... from this value? */
/* Hint:
This is used as some kind of interruption of the 600s
transition-delay in order to achieve the parent un-hover effect.
I would like to set the width to 10px here as well but this will
result in having no effect on the width of the enlarged child when
un-hovering the parent. */
}
<div class="parent">
<div class="child">
</div>
</div>
一个小观察
相关浏览器有 Firefox 和 Chrome。在 Firefox 中,可以执行以下操作:
.parent .child {
/* ... */
transition: width 0.5s ease 600s;
width: calc(10px);
}
.parent:not(:hover) .child {
transition: width 0.5s ease 0s;
width: 10px;
}
Question
为什么宽度属性的值必须不同才能使非悬停效果按预期工作?
抱歉 - 我误解了你问题中发生的情况。
我用简化的案例做了一个新的片段:
#a, #b {
width: 200px;
height: 100px;
border: solid 1px black;
display: inline-block;
background-color: lightgreen;
margin-top: 50px;
}
#a {
margin-right: -5px;
}
#container {
width: 400px;
height: 50px;
border: solid 1px black;
margin: 0px;
}
#child {
width: 0px;
height: 50px;
position: absolute;
background-color: blue;
}
#child {
transition: width 0.5s;
width: 400px;
}
#a:hover ~ #container #child {
transition: width 10s;
width: 0px;
}
#b:hover ~ #container #child {
transition: width 0.5s;
width: 0px;
}
<div id="a">A</div>
<div id="b">B</div>
<div id="container">
<div id="child"></div>
</div>
将鼠标悬停在 A 上,然后(在过渡结束之前)将鼠标悬停在 B 上。您将看到相同的行为:过渡继续保持不变。
原因是当悬停 a 时,宽度(作为元素的属性)为 0px。 (不是计算出的宽度,正在转换)。
因此,当你将鼠标悬停在 B 上时,新的 0px 样式不会触发属性更改,hende 也不会启动新的过渡。
旧答案
规格的关键部分是这个:(强调我的)
反转跃迁规范 https://www.w3.org/TR/css3-transitions/#reversing
为了满足此期望,当为具有当前正在运行的转换(其起始值经过反向调整)的元素上的属性(此后称为新转换)启动转换时是一样的作为新过渡(此后称为旧过渡)的最终值,实现必须取消旧过渡 [...] 并按如下方式调整新过渡(在遵循计算组合持续时间、开始时间和时间的规则之前)时间结束): [...]
所以,当新的宽度与旧的宽度相同时,并不是说取消悬停没有效果,而是效果是very缓慢(600 秒),因为浏览器正在反转正在运行的转换。
为了证明这一点,我设置了一个片段,其中最后一条规则的宽度相同(10px)。
并且延迟设置为10秒。
将鼠标悬停在子项上,然后将其取消悬停,从而离开父项。 10秒后你会看到子宽度被修改了。
.parent {
border: 1px solid orange;
padding: 20px;
width: 400px;
}
.parent .child {
display: inline-block;
height: 40px;
background: blue;
transition: width 0.5s ease 10s;
width: 10px;
}
.parent .child:hover {
transition-delay: 0s;
width: 100px;
}
.parent:not(:hover) .child {
transition: width 0.5s ease 0s;
width: 10px;
<div class="parent">
<div class="child">
</div>
</div>
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)