使用透视和变换时如何控制z-index?
How to control z-index when using perspective and transform?
我读过很多关于 z-index 以及变换和透视如何破坏他的上下文的页面。我明白为什么我的代码不工作我不知道如何让它工作(或至少使用和替代)。
如图所示,select 菜单被下面的卡片覆盖。
这里是问题重现的片段:
.square { position: relative; width: 100%; padding-bottom: 100%; }
.square>* { position: absolute; width: 100%; height: 100%; }
/* flip */
/* u -> uncontroled / c -> controled */
.flip { perspective: 200em; }
.flip .front, .flip .back {
-webkit-backface-visibility: hidden; -moz-backface-visibility: hidden;
backface-visibility: hidden; position: absolute;
top: 0; left: 0; right: 0; bottom: 0;
}
@supports (-webkit-transform-style: preserve-3d) or (-moz-transform-style: preserve-3d) or (transform-style: preserve-3d) {
.flip .front, .flip .back {
-webkit-transform-style: preserve-3d; -moz-transform-style: preserve-3d; transform-style: preserve-3d; transition: 1s;
}
}
/* -> horizontal */
.flip .front { z-index: 2; transform: rotateY(0deg); perspective: none;}
.flip .back { transform: rotateY(-180deg); }
.flip.u:hover .back, .flip.c.active .back { transform: rotateY(0deg); }
.flip.u:hover .front, .flip.c.active .front { transform: rotateY(180deg); }
/* -> vertical */
.flip.vertical .back { transform: rotateX(-180deg); }
.flip.vertical.u:hover .back, .flip.vertical.c.active .back { transform: rotateX(0deg); }
.flip.vertical.u:hover .front, .flip.vertical.c.active .front { transform: rotateX(180deg); }
.test {
position: absolute; top: 70%; left: 10%; background-color: green;
height: 100px; width: 10px; z-index: 100;
}
<div style="width: 100px; background-color: black">
<div class="square flip u">
<div class="front" style="background-color: blue">
Front
<div class="test"></div>
</div>
<div class="back" style="background-color: red">Back</div>
</div>
<hr >
<div class="square flip u">
<div class="front" style="background-color: blue">Front</div>
<div class="back" style="background-color: red">Back</div>
</div>
</div>
我需要的是显示在所有人面前的<div class="test">
。喜欢this。但我不想在方形 div 上设置 z-index,因为它们将被放置在 flex layout Grid 中。
有没有办法让某个元素始终呈现在所有其他元素之前?不知道他放在哪里或堆栈上下文发生了什么。
我所做的只是将带有 class .test
的 div
移动到带有翻转元素的 div
之外。
.square {
position: relative;
width: 100%;
padding-bottom: 100%;
}
.square>* {
position: absolute;
width: 100%;
height: 100%;
}
/* flip */
/* u -> uncontroled / c -> controled */
.flip {
perspective: 200em;
}
.flip .front,
.flip .back {
-webkit-backface-visibility: hidden;
-moz-backface-visibility: hidden;
backface-visibility: hidden;
position: absolute;
top: 0;
left: 0;
right: 0;
bottom: 0;
}
@supports (-webkit-transform-style: preserve-3d) or (-moz-transform-style: preserve-3d) or (transform-style: preserve-3d) {
.flip .front,
.flip .back {
-webkit-transform-style: preserve-3d;
-moz-transform-style: preserve-3d;
transform-style: preserve-3d;
transition: 1s;
}
}
/* -> horizontal */
.flip .front {
z-index: 2;
transform: rotateY(0deg);
perspective: none;
}
.flip .back {
transform: rotateY(-180deg);
}
.flip.u:hover .back,
.flip.c.active .back {
transform: rotateY(0deg);
}
.flip.u:hover .front,
.flip.c.active .front {
transform: rotateY(180deg);
}
/* -> vertical */
.flip.vertical .back {
transform: rotateX(-180deg);
}
.flip.vertical.u:hover .back,
.flip.vertical.c.active .back {
transform: rotateX(0deg);
}
.flip.vertical.u:hover .front,
.flip.vertical.c.active .front {
transform: rotateX(180deg);
}
.test {
position: absolute;
top: 30%;
left: 3%;
background-color: green;
height: 100px;
width: 10px;
z-index: 10;
}
<div style="width: 100px; background-color: black">
<div class="square flip u">
<div class="front" style="background-color: blue">
Front
</div>
<div class="back" style="background-color: red">Back</div>
</div>
<div class="test"></div>
<hr>
<div class="square flip u">
<div class="front" style="background-color: blue">Front</div>
<div class="back" style="background-color: red">Back</div>
</div>
</div>
在过去的几年里没有人找到解决方案,所以这里是我最终所做的(作为解决我的特定问题的替代方案):
我刚刚使用 js 更改了所有子元素的 z-index,使首先具有更高 z-index 的那些子元素。
var targets = document.getElementsByClassName("invertChildZOrder");
var i;
for (i = 0; i < targets.length; i++) {
target = targets[i];
for (var i = 0; i < target.childNodes.length; i++) {
var childNode = target.childNodes[i];
if (childNode.className == "square flip u") {
childNode.style.zIndex = "" + (target.childNodes.length - i);
}
}
}
.square { position: relative; width: 100%; padding-bottom: 100%; }
.square>* { position: absolute; width: 100%; height: 100%; }
/* flip */
/* u -> uncontroled / c -> controled */
.flip { perspective: 200em; }
.flip .front, .flip .back {
-webkit-backface-visibility: hidden; -moz-backface-visibility: hidden;
backface-visibility: hidden; position: absolute;
top: 0; left: 0; right: 0; bottom: 0;
}
@supports (-webkit-transform-style: preserve-3d) or (-moz-transform-style: preserve-3d) or (transform-style: preserve-3d) {
.flip .front, .flip .back {
-webkit-transform-style: preserve-3d; -moz-transform-style: preserve-3d; transform-style: preserve-3d; transition: 1s;
}
}
/* -> horizontal */
.flip .front { z-index: 2; transform: rotateY(0deg); perspective: none;}
.flip .back { transform: rotateY(-180deg); }
.flip.u:hover .back, .flip.c.active .back { transform: rotateY(0deg); }
.flip.u:hover .front, .flip.c.active .front { transform: rotateY(180deg); }
/* -> vertical */
.flip.vertical .back { transform: rotateX(-180deg); }
.flip.vertical.u:hover .back, .flip.vertical.c.active .back { transform: rotateX(0deg); }
.flip.vertical.u:hover .front, .flip.vertical.c.active .front { transform: rotateX(180deg); }
.test {
position: absolute; top: 70%; left: 10%; background-color: green;
height: 100px; width: 10px; z-index: 100;
}
<div class="invertChildZOrder" style="width: 100px; background-color: black">
<div class="square flip u">
<div class="front" style="background-color: blue">
Front
<div class="test"></div>
</div>
<div class="back" style="background-color: red">Back</div>
</div>
<hr >
<div class="square flip u">
<div class="front" style="background-color: blue">Front</div>
<div class="back" style="background-color: red">Back</div>
</div>
</div>
如你所想。这只能部分解决问题。如果按钮上的方块有另一个菜单,但这次是向上而不是向下,我们也会遇到同样的问题。
我采取了不同的方法。动画完成后,我删除了动画 class。我认为这是一个更简单的解决方案(我也浪费了数小时试图弄清楚发生了什么......)
我读过很多关于 z-index 以及变换和透视如何破坏他的上下文的页面。我明白为什么我的代码不工作我不知道如何让它工作(或至少使用和替代)。
如图所示,select 菜单被下面的卡片覆盖。
这里是问题重现的片段:
.square { position: relative; width: 100%; padding-bottom: 100%; }
.square>* { position: absolute; width: 100%; height: 100%; }
/* flip */
/* u -> uncontroled / c -> controled */
.flip { perspective: 200em; }
.flip .front, .flip .back {
-webkit-backface-visibility: hidden; -moz-backface-visibility: hidden;
backface-visibility: hidden; position: absolute;
top: 0; left: 0; right: 0; bottom: 0;
}
@supports (-webkit-transform-style: preserve-3d) or (-moz-transform-style: preserve-3d) or (transform-style: preserve-3d) {
.flip .front, .flip .back {
-webkit-transform-style: preserve-3d; -moz-transform-style: preserve-3d; transform-style: preserve-3d; transition: 1s;
}
}
/* -> horizontal */
.flip .front { z-index: 2; transform: rotateY(0deg); perspective: none;}
.flip .back { transform: rotateY(-180deg); }
.flip.u:hover .back, .flip.c.active .back { transform: rotateY(0deg); }
.flip.u:hover .front, .flip.c.active .front { transform: rotateY(180deg); }
/* -> vertical */
.flip.vertical .back { transform: rotateX(-180deg); }
.flip.vertical.u:hover .back, .flip.vertical.c.active .back { transform: rotateX(0deg); }
.flip.vertical.u:hover .front, .flip.vertical.c.active .front { transform: rotateX(180deg); }
.test {
position: absolute; top: 70%; left: 10%; background-color: green;
height: 100px; width: 10px; z-index: 100;
}
<div style="width: 100px; background-color: black">
<div class="square flip u">
<div class="front" style="background-color: blue">
Front
<div class="test"></div>
</div>
<div class="back" style="background-color: red">Back</div>
</div>
<hr >
<div class="square flip u">
<div class="front" style="background-color: blue">Front</div>
<div class="back" style="background-color: red">Back</div>
</div>
</div>
我需要的是显示在所有人面前的<div class="test">
。喜欢this。但我不想在方形 div 上设置 z-index,因为它们将被放置在 flex layout Grid 中。
有没有办法让某个元素始终呈现在所有其他元素之前?不知道他放在哪里或堆栈上下文发生了什么。
我所做的只是将带有 class .test
的 div
移动到带有翻转元素的 div
之外。
.square {
position: relative;
width: 100%;
padding-bottom: 100%;
}
.square>* {
position: absolute;
width: 100%;
height: 100%;
}
/* flip */
/* u -> uncontroled / c -> controled */
.flip {
perspective: 200em;
}
.flip .front,
.flip .back {
-webkit-backface-visibility: hidden;
-moz-backface-visibility: hidden;
backface-visibility: hidden;
position: absolute;
top: 0;
left: 0;
right: 0;
bottom: 0;
}
@supports (-webkit-transform-style: preserve-3d) or (-moz-transform-style: preserve-3d) or (transform-style: preserve-3d) {
.flip .front,
.flip .back {
-webkit-transform-style: preserve-3d;
-moz-transform-style: preserve-3d;
transform-style: preserve-3d;
transition: 1s;
}
}
/* -> horizontal */
.flip .front {
z-index: 2;
transform: rotateY(0deg);
perspective: none;
}
.flip .back {
transform: rotateY(-180deg);
}
.flip.u:hover .back,
.flip.c.active .back {
transform: rotateY(0deg);
}
.flip.u:hover .front,
.flip.c.active .front {
transform: rotateY(180deg);
}
/* -> vertical */
.flip.vertical .back {
transform: rotateX(-180deg);
}
.flip.vertical.u:hover .back,
.flip.vertical.c.active .back {
transform: rotateX(0deg);
}
.flip.vertical.u:hover .front,
.flip.vertical.c.active .front {
transform: rotateX(180deg);
}
.test {
position: absolute;
top: 30%;
left: 3%;
background-color: green;
height: 100px;
width: 10px;
z-index: 10;
}
<div style="width: 100px; background-color: black">
<div class="square flip u">
<div class="front" style="background-color: blue">
Front
</div>
<div class="back" style="background-color: red">Back</div>
</div>
<div class="test"></div>
<hr>
<div class="square flip u">
<div class="front" style="background-color: blue">Front</div>
<div class="back" style="background-color: red">Back</div>
</div>
</div>
在过去的几年里没有人找到解决方案,所以这里是我最终所做的(作为解决我的特定问题的替代方案):
我刚刚使用 js 更改了所有子元素的 z-index,使首先具有更高 z-index 的那些子元素。
var targets = document.getElementsByClassName("invertChildZOrder");
var i;
for (i = 0; i < targets.length; i++) {
target = targets[i];
for (var i = 0; i < target.childNodes.length; i++) {
var childNode = target.childNodes[i];
if (childNode.className == "square flip u") {
childNode.style.zIndex = "" + (target.childNodes.length - i);
}
}
}
.square { position: relative; width: 100%; padding-bottom: 100%; }
.square>* { position: absolute; width: 100%; height: 100%; }
/* flip */
/* u -> uncontroled / c -> controled */
.flip { perspective: 200em; }
.flip .front, .flip .back {
-webkit-backface-visibility: hidden; -moz-backface-visibility: hidden;
backface-visibility: hidden; position: absolute;
top: 0; left: 0; right: 0; bottom: 0;
}
@supports (-webkit-transform-style: preserve-3d) or (-moz-transform-style: preserve-3d) or (transform-style: preserve-3d) {
.flip .front, .flip .back {
-webkit-transform-style: preserve-3d; -moz-transform-style: preserve-3d; transform-style: preserve-3d; transition: 1s;
}
}
/* -> horizontal */
.flip .front { z-index: 2; transform: rotateY(0deg); perspective: none;}
.flip .back { transform: rotateY(-180deg); }
.flip.u:hover .back, .flip.c.active .back { transform: rotateY(0deg); }
.flip.u:hover .front, .flip.c.active .front { transform: rotateY(180deg); }
/* -> vertical */
.flip.vertical .back { transform: rotateX(-180deg); }
.flip.vertical.u:hover .back, .flip.vertical.c.active .back { transform: rotateX(0deg); }
.flip.vertical.u:hover .front, .flip.vertical.c.active .front { transform: rotateX(180deg); }
.test {
position: absolute; top: 70%; left: 10%; background-color: green;
height: 100px; width: 10px; z-index: 100;
}
<div class="invertChildZOrder" style="width: 100px; background-color: black">
<div class="square flip u">
<div class="front" style="background-color: blue">
Front
<div class="test"></div>
</div>
<div class="back" style="background-color: red">Back</div>
</div>
<hr >
<div class="square flip u">
<div class="front" style="background-color: blue">Front</div>
<div class="back" style="background-color: red">Back</div>
</div>
</div>
如你所想。这只能部分解决问题。如果按钮上的方块有另一个菜单,但这次是向上而不是向下,我们也会遇到同样的问题。
我采取了不同的方法。动画完成后,我删除了动画 class。我认为这是一个更简单的解决方案(我也浪费了数小时试图弄清楚发生了什么......)