CSS Filters break 3D transforms

前端 未结 1 1091
[愿得一人]
[愿得一人] 2021-01-05 14:58

I was experimenting with CSS transforms when I found that filters flatten the transforms, just like transform-style: flat.

相关标签:
1条回答
  • 2021-01-05 15:20

    As per W3C Transforms Spec:

    The following CSS property values require the user agent to create a flattened representation of the descendant elements before they can be applied, and therefore override the behavior of transform-style: preserve-3d:

    overflow: any value other than visible.

    filter: any value other than none.

    clip: any value other than auto.

    clip-path: any value other than none.

    isolation: used value of isolate.

    mask-image: any value other than none.

    mask-box-image-source: any value other than none.

    mix-blend-mode: any value other than normal.

    The computed value of transform-style is not affected.

    This is the reason why the 3D transforms are broken and the layers are flattened when you toggle on the filters. The one workaround that I know for this situation is creating the entire cube using sibling elements and apply the filter on the sibling elements directly instead of applying on the parent.

    var toggleFilter = function() {
      var div = document.getElementById("cube")
      if (div.className == "cube") {
        div.className = "cube filter"
      } else {
        div.className = "cube"
      }
    }
    * {
      transform-style: preserve-3d
    }
    div.cube {
      position: relative;
      height: 100px;
      width: 100px;
      transform: rotateX(45deg) rotateZ(45deg);
    }
    div.face0 {
      position: absolute;
      content: '';
      height: 100%;
      width: 100%;
      top: 0px;
      left: 0px;
      background: blue;
      border: solid 2px black;
      box-sizing: border-box;
    }
    div.face1 {
      content: "";
      height: 100px;
      width: 100px;
      background: green;
      transform: rotateY(90deg) translateZ(50px) translateX(50px);
      border: solid 2px black;
      box-sizing: border-box;
    }
    div.face2 {
      content: "";
      height: 100px;
      width: 100px;
      background: red;
      transform: rotateY(90deg) rotateX(-90deg) translateZ(-50px) translateX(50px);
      border: solid 2px black;
      box-sizing: border-box;
    }
    div.perspective {
      perspective: 900px;
      position: absolute;
      margin: 50px;
    }
    .filter .face0,
    .filter .face1,
    .filter .face2 {
      filter: opacity(25%);
      -webkit-filter: opacity(25%);
    }
    <div class="perspective">
      <div id="cube" class="cube">
        <div class="face0"></div>
        <div class="face1"></div>
        <div class="face2"></div>
      </div>
    </div>
    <button onclick="toggleFilter()">Toggle .Filter</button>

    0 讨论(0)
提交回复
热议问题