CSS-only Acrylic Material from Fluent Design System
Asked Answered
T

4

45

With the advent of Microsoft's Fluent Design System and the propagation of the new Acrylic Material around the Windows ecosystem, I thought it would be great to use it in some Web layouts.

Acoording to the spec, the composition of an acrylic layer is:

Image

So I went to try a CSS-only approach inspired by the layers in that picture, this way:

body {
  margin: 0;
  font: 1em/1.4 Sans-serif;
  background: url("https://cdn.pixabay.com/photo/2017/03/27/16/50/beach-2179624_1280.jpg") center center;
  background-size: 100vw auto;
}

main {
  display: flex;
  align-items: center;
  justify-content: center;
  height: 100vh;
}

.acrylic {
  padding: 4em 6em;
  position: relative;
  overflow: hidden;
}

.acrylic::before {
  background: url("https://cdn.pixabay.com/photo/2017/03/27/16/50/beach-2179624_1280.jpg") center center;
  background-size: 100vw auto;
  filter: blur(10px);
  content: "";
  position: absolute;
  left: -10px;
  top: -10px;
  width: calc(100% + 20px);
  height: calc(100% + 20px);
  z-index: -1;
}

.acrylic::after {
  content: "";
  position: absolute;
  left: 0;
  top: 0;
  right: 0;
  bottom: 0;
  z-index: -1;
  opacity: 0.65;
  border: 1px solid #fff;
  background: #fff;
  background-image: url(data:image/png;base64,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);
}

.shadow {
  border-radius: 1px;
  box-shadow: 0 10px 30px rgba(0, 0, 0, 0.1), 0 1px 8px rgba(0, 0, 0, 0.2);
}
<main>
  <div class="acrylic shadow">
    Acrylic material!
  </div>
</main>

The result is really close to the spec and is also responsive, but has a big problem: just stack another .acrylic div and the background trick doesn't work anymore.

The question is: is there some smarter way to gaussian blur without duplicating the body background for each children? Or maybe some smarter way to dinamically calculate its position?


2022 Update

When I originally posted this question, the backdrop-filter CSS feature was an experimental thing not enabled even in Chrome, so I was asking for an alternative solution, if possible, at the time.

Time passes... Finally it's enabled by default on all browsers over 0.5% users. So it's really simplier to solve nowadays than it was before.

Transalpine answered 13/6, 2017 at 13:1 Comment(1)
I believe my answer does that perfectly without compromising any functionality and even adding in more browser compatibility. I hope you will consider it.Tiflis
T
10

2022 Update

TL;DR: Use backdrop-filter for the blur effect and that's it.

When I originally posted the question, the backdrop-filter CSS feature was an experimental thing not enabled even in Chrome, so I was asking for an alternative solution, if possible, at the time.

Since then, the backdrop-filter feature shipped in Chrome 76 at July 29ᵗʰ 2019, already turning it into a viable option for progressive enhancement use cases. Finally, after years of recurring postpones, Firefox released it enabled by default in 103 version, at July 26ᵗʰ 2022.

Now with a theoretical cross-browser support on about 95%, and a practical 100% support considering browsers with more than 0.5% of users, it's clearly the option to go:

/* Now all the acrylic layer is just only one class! */
.acrylic {
  /* Parent background + Gaussian blur */
  backdrop-filter: blur(10px);
  -webkit-backdrop-filter: blur(10px); /* Safari */

  /* Exclusion blend */
  background-blend-mode: exclusion;

  /* Color/tint overlay + Opacity */
  background: rgba(255, 255, 255, .6);

  /* Tiled noise texture */
  background-image: url(data:image/png;base64,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);
}

/* Other styles for sample purposes... */
body {
  margin: 0;
  padding: 1.5em;
  font: 1em/1.4 Sans-serif;

  /* Now our background image is defined only in the body! */
  background: url("https://cdn.pixabay.com/photo/2017/03/27/16/50/beach-2179624_1280.jpg") center center;
  background-size: 100vw auto;
}

main {
  display: grid;
  gap: 1.5rem;
  justify-content: center;
  grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));
  grid-auto-rows: minmax(120px, auto);
}

div {
  padding: 1.5em;
  border-radius: 1px;
  border: 1px solid rgba(255, 255, 255, .2);
  box-shadow: 0 10px 30px rgba(0, 0, 0, .1), 0 1px 8px rgba(0, 0, 0, .2);
  text-align: center;
  display: flex;
  align-items: center;
  justify-content: center;
}
<main>
  <div class="acrylic">
    Acrylic material!
  </div>

  <div class="acrylic">
    <div class="acrylic">
      Acrylic inside acrylic!
    </div>
  </div>

  <div class="acrylic">
    Acrylic material!
  </div>

  <div class="acrylic">
    Acrylic material!
  </div>
</main>
Transalpine answered 8/8, 2019 at 17:24 Comment(0)
C
38
EDIT: 2022-05-07

Made backdrop-filter the first option with much better browser support now.


I can think of two ways to do this...

  1. backdrop-filter on .acrylic for modern browsers

  2. Blurred bg on .acrylic for all (including legacy) browsers

1. backdrop-filter on .acrylic (Modern browsers)

main {
  display: flex;
  align-items: center;
  justify-content: center;
  height: 100vh;
}

.acrylic {
  padding: 4em 6em;
  position: relative;
  background: rgba(0,0,0,0.5);
  -webkit-backdrop-filter: blur(10px);
  backdrop-filter: blur(10px);
  margin: 7px;
}

body {
  background: url("https://images.unsplash.com/photo-1452723312111-3a7d0db0e024?w=700") center/cover;
  background-attachment: fixed;
  margin: 0;
  font: 1em/1.4 Sans-serif;
  color: #fff;
}
<main>
  <div class="acrylic shadow">
    Acrylic material!
  </div>
  <div class="acrylic shadow">
    Acrylic material!
  </div>
</main>

<main>
  <div class="acrylic shadow">
    Acrylic material!
  </div>
  <div class="acrylic shadow">
    Acrylic material!
  </div>
</main>

<main>
  <div class="acrylic shadow">
    Acrylic material!
  </div>
</main>

2. Blurred bg on .acrylic (Legacy browsers)

We duplicate bg on .acrylic elements too, because just bringing down opacity will show the content behind them not in them, which AFAIK is not covered by blur filter...

Smart way to calc positions would be to set background-attachment: fixed for both parent element (body) and .acrylic guys, this will allow you to have multiple .acrylic guys as well ;)

Since we use same background for parent and children, we can club them together ;)

body, .acrylic::before {
  background: url("IMG_URL_HERE") center/cover;
  background-attachment: fixed;
}

Here is a working snippet ;) Turned opacity on .acrylic:after a bit down so background is a bit more visible ;)

body {
  margin: 0;
  font: 1em/1.4 Sans-serif;
}

body, .acrylic::before {
  background: url("https://images.unsplash.com/photo-1452723312111-3a7d0db0e024?w=700") center/cover;
  background-attachment: fixed;
}

main {
  display: flex;
  align-items: center;
  justify-content: center;
  height: 100vh;
}

.acrylic {
  padding: 4em 6em;
  position: relative;
  overflow: hidden;
  margin: 1em;
}

.acrylic::before {
  filter: blur(10px);
  content: "";
  position: absolute;
  left: -10px;
  top: -10px;
  width: calc(100% + 20px);
  height: calc(100% + 20px);
  z-index: -1;
}

.acrylic::after {
  content: "";
  position: absolute;
  left: 0;
  top: 0;
  right: 0;
  bottom: 0;
  z-index: -1;
  opacity: 0.35;
  border: 1px solid #fff;
  background: #fff;
  background-image: url(data:image/png;base64,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);
}

.shadow {
  border-radius: 1px;
  box-shadow: 0 10px 30px rgba(0, 0, 0, 0.1), 0 1px 8px rgba(0, 0, 0, 0.2);
}
<main>
  <div class="acrylic shadow">
    Acrylic material!
  </div>
  <div class="acrylic shadow">
    Acrylic material!
  </div>
</main>

<main>
  <div class="acrylic shadow">
    Acrylic material!
  </div>
  <div class="acrylic shadow">
    Acrylic material!
  </div>
</main>

<main>
  <div class="acrylic shadow">
    Acrylic material!
  </div>
</main>
Culottes answered 18/6, 2017 at 4:8 Comment(3)
Your image didn't seem to work for me, so added one from unsplash ;) Let me know how it work for you ;)Culottes
I'm curious, is the frequently used ;) in your answer some kind of punctuation mark or just a smiley? :D And to contribute something useful: caniuse.com/backdrop-filter.Sungkiang
Well, when I use a smiley, I skip a comma or full stop ;) Thanks for the contribution :)Culottes
T
16

This answer solves the problem and I've enhanced it aswell.

I think the only problem you had was background alignment applied to the ::before and the body were different. So by combining the CSS used into one, I've shortcutted this to make updating and editing it easier.

I used background:rgba() instead of #hex values to give more flexibility over the opacity controls.

I've added notes throughout the CSS to explain the changes I've made to make them more apparent.

NOTE: Removing the opacity from the ::after class causes transparency to increase and increases the visibility of the noise texture. I believe it is being caused by the noise texture itself being semi transparent, but it is an odd behaviour, if anyone else knows and has a better explanation I'd be interested to know. I've added classes .nested and .parent. as it may be preferable to have control over these things separately. I've removed .parent in the second example and both in the third.

Update: Noticed the exclusion blend filter mentioned in spec wasn't included, so I've added that in too. Provided sources below the snippet.

Hope this helped. :)

CSS & HTML Snippet with 3 examples:

/* Adding the background source for 
both elements together simplifies editing. 
Changing the background color #333 to #fff 
will produce much more intence effect on 
the filter blend */

html,
.acrylic:before {
  background: #333 url(https://source.unsplash.com/1600x900/?nature) 50% 100% fixed;
  background-size: cover;
}

body {
  margin: 0;
  font: 1em/1.4 Sans-serif;
}


/*div spacings*/

div {
  margin: 5px;
}

main {
  display: flex;
  align-items: center;
  justify-content: center;
  flex-flow: row wrap;
  height: 100vh;
}

.acrylic {
  padding: 4em 6em;
  position: relative;
  overflow: hidden;
}


/*Added browser compatibility for blurring added the exclusion blend filter as explained in the original document*/

.acrylic::before {
  content: '';
  position: absolute;
  z-index: -1;
  height: 100%;
  top: 0;
  right: 0;
  left: 0;
  filter: blur(8px);
  -webkit-filter: blur(8px);
  -moz-filter: blur(8px);
  -o-filter: blur(8px);
  -ms-filter: blur(8px);
  background-blend-mode: exclusion;
}


/*made color rgba removed opacity property*/

.acrylic::after {
  content: "";
  position: absolute;
  height: 100%;
  left: 0;
  top: 0;
  right: 0;
  bottom: 0;
  z-index: -1;
  border: 1px solid #fff;
  background-image: url(data:image/png;base64,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);
}


/*Individual control over 
.nested and .parent opacity and color.*/

.parent::after {
  background-color: rgba(230, 240, 255, 0.50);
  opacity: 0.60;
}

.child::after {
  background-color: rgba(230, 240, 255, 0.30);
  opacity: 0.60;
}

.shadow {
  box-shadow: 0 10px 30px rgba(0, 0, 0, 0.2), 0 1px 8px rgba(0, 0, 0, 0.4);
}
<body>
  <main>
    <div class="acrylic shadow parent">
      <div class="acrylic child">
        Acrylic material! <br />.parent on .child on
      </div>
    </div>
    <div class="acrylic shadow">
      <div class="acrylic child">
        Acrylic material! <br />.parent off .child on
      </div>
    </div>
    <div class="acrylic shadow">
      <div class="acrylic">
        Acrylic material! <br />.parent off .child off
      </div>
    </div>
  </main>
</body>

Sources and extra notes:

You can find a source for front glass effect on CSS Tricks here.

The duplicate image technique requires maintaining a blurred image along with the original, which can become a pain if you need to reuse the effect for multiple images. For example, responsive designs may require swapping in different images at different screen sizes. Or, template layouts may drop in images dynamically (eg, a different header image for every blog post). For these cases, it would be nice to generate the effect using only the source image. After all, we're just blurring it.

They also say that if you want to offer even more browser support you can add in SVG filter as a fall back, although I haven't added it to my own snippet they say this:

CSS Filters are somewhat new. That means they may be vendor prefixed, and that their browser support is not yet universal. However, filters have a longer history in SVG, and applying SVG filters to HTML content via CSS has wider browser support. You can easily add them as a fallback for when CSS filters are not supported. The above demo actually does just that.

To add an SVG filter, we include some inline SVG in our HTML markup, and reference the filter with a url(). Pro tip: An alternative is to encode the SVG filter and reference as a data url, but that format is a bit more difficult to read in an article.

And provided a code example

SVG:

<svg xmlns="http://www.w3.org/2000/svg" version="1.1">
  <defs>
    <filter id="blur">
      <feGaussianBlur stdDeviation="5" />
    </filter>
  </defs>
</svg>

CSS

.glass::before {
    background-image: url('pelican.jpg');
    /* Fallback to SVG filters */
    filter: url('#blur');
    filter: blur(5px);
}

For more about the CSS filter blends, go here https://css-tricks.com/basics-css-blend-modes

Tiflis answered 19/6, 2017 at 12:42 Comment(0)
T
10

2022 Update

TL;DR: Use backdrop-filter for the blur effect and that's it.

When I originally posted the question, the backdrop-filter CSS feature was an experimental thing not enabled even in Chrome, so I was asking for an alternative solution, if possible, at the time.

Since then, the backdrop-filter feature shipped in Chrome 76 at July 29ᵗʰ 2019, already turning it into a viable option for progressive enhancement use cases. Finally, after years of recurring postpones, Firefox released it enabled by default in 103 version, at July 26ᵗʰ 2022.

Now with a theoretical cross-browser support on about 95%, and a practical 100% support considering browsers with more than 0.5% of users, it's clearly the option to go:

/* Now all the acrylic layer is just only one class! */
.acrylic {
  /* Parent background + Gaussian blur */
  backdrop-filter: blur(10px);
  -webkit-backdrop-filter: blur(10px); /* Safari */

  /* Exclusion blend */
  background-blend-mode: exclusion;

  /* Color/tint overlay + Opacity */
  background: rgba(255, 255, 255, .6);

  /* Tiled noise texture */
  background-image: url(data:image/png;base64,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);
}

/* Other styles for sample purposes... */
body {
  margin: 0;
  padding: 1.5em;
  font: 1em/1.4 Sans-serif;

  /* Now our background image is defined only in the body! */
  background: url("https://cdn.pixabay.com/photo/2017/03/27/16/50/beach-2179624_1280.jpg") center center;
  background-size: 100vw auto;
}

main {
  display: grid;
  gap: 1.5rem;
  justify-content: center;
  grid-template-columns: repeat(auto-fit, minmax(250px, 1fr));
  grid-auto-rows: minmax(120px, auto);
}

div {
  padding: 1.5em;
  border-radius: 1px;
  border: 1px solid rgba(255, 255, 255, .2);
  box-shadow: 0 10px 30px rgba(0, 0, 0, .1), 0 1px 8px rgba(0, 0, 0, .2);
  text-align: center;
  display: flex;
  align-items: center;
  justify-content: center;
}
<main>
  <div class="acrylic">
    Acrylic material!
  </div>

  <div class="acrylic">
    <div class="acrylic">
      Acrylic inside acrylic!
    </div>
  </div>

  <div class="acrylic">
    Acrylic material!
  </div>

  <div class="acrylic">
    Acrylic material!
  </div>
</main>
Transalpine answered 8/8, 2019 at 17:24 Comment(0)
P
0

Is there some smarter way to gaussian blur without duplicating the body background for each children?

As far as I know there is no smarter way in this case to achieve that, since the background image and the filter have to be set to the same div to create this desired effect.

Or maybe some smarter way to dynamically calculate its position?

As far as I understood, the issue is that with every additional div .acrylic the background part of the image gets duplicated.

Since you're using the same background image you could fix this by simply adding background-attachment: fixed to the div .acrylic::before.

body {
  margin: 0;
  font: 1em/1.4 Sans-serif;
  background: url("http://www.wallpapers-web.com/data/out/191/5484624-sunset-wallpapers.jpg") center center;
  background-size: 100vw auto;
}

main {
  display: flex;
  align-items: center;
  justify-content: center;
  height: 100vh;
}

.acrylic {
  padding: 4em 6em;
  position: relative;
  overflow: hidden;
}

.acrylic::before {
  background: url("http://www.wallpapers-web.com/data/out/191/5484624-sunset-wallpapers.jpg") center center;
  background-size: 100vw auto;
  background-attachment: fixed;
  filter: blur(10px);
  content: "";
  position: absolute;
  left: -10px;
  top: -10px;
  width: calc(100% + 20px);
  height: calc(100% + 20px);
  z-index: -1;
}

.acrylic::after {
  content: "";
  position: absolute;
  left: 0;
  top: 0;
  right: 0;
  bottom: 0;
  z-index: -1;
  opacity: 0.65;
  border: 1px solid #fff;
  background: #fff;
  background-image: url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAADIAAAAyCAMAAAAp4XiDAAAAUVBMVEWFhYWDg4N3d3dtbW17e3t1dXWBgYGHh4d5eXlzc3OLi4ubm5uVlZWPj4+NjY19fX2JiYl/f39ra2uRkZGZmZlpaWmXl5dvb29xcXGTk5NnZ2c8TV1mAAAAG3RSTlNAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEAvEOwtAAAFVklEQVR4XpWWB67c2BUFb3g557T/hRo9/WUMZHlgr4Bg8Z4qQgQJlHI4A8SzFVrapvmTF9O7dmYRFZ60YiBhJRCgh1FYhiLAmdvX0CzTOpNE77ME0Zty/nWWzchDtiqrmQDeuv3powQ5ta2eN0FY0InkqDD73lT9c9lEzwUNqgFHs9VQce3TVClFCQrSTfOiYkVJQBmpbq2L6iZavPnAPcoU0dSw0SUTqz/GtrGuXfbyyBniKykOWQWGqwwMA7QiYAxi+IlPdqo+hYHnUt5ZPfnsHJyNiDtnpJyayNBkF6cWoYGAMY92U2hXHF/C1M8uP/ZtYdiuj26UdAdQQSXQErwSOMzt/XWRWAz5GuSBIkwG1H3FabJ2OsUOUhGC6tK4EMtJO0ttC6IBD3kM0ve0tJwMdSfjZo+EEISaeTr9P3wYrGjXqyC1krcKdhMpxEnt5JetoulscpyzhXN5FRpuPHvbeQaKxFAEB6EN+cYN6xD7RYGpXpNndMmZgM5Dcs3YSNFDHUo2LGfZuukSWyUYirJAdYbF3MfqEKmjM+I2EfhA94iG3L7uKrR+GdWD73ydlIB+6hgref1QTlmgmbM3/LeX5GI1Ux1RWpgxpLuZ2+I+IjzZ8wqE4nilvQdkUdfhzI5QDWy+kw5Wgg2pGpeEVeCCA7b85BO3F9DzxB3cdqvBzWcmzbyMiqhzuYqtHRVG2y4x+KOlnyqla8AoWWpuBoYRxzXrfKuILl6SfiWCbjxoZJUaCBj1CjH7GIaDbc9kqBY3W/Rgjda1iqQcOJu2WW+76pZC9QG7M00dffe9hNnseupFL53r8F7YHSwJWUKP2q+k7RdsxyOB11n0xtOvnW4irMMFNV4H0uqwS5ExsmP9AxbDTc9JwgneAT5vTiUSm1E7BSflSt3bfa1tv8Di3R8n3Af7MNWzs49hmauE2wP+ttrq+AsWpFG2awvsuOqbipWHgtuvuaAE+A1Z/7gC9hesnr+7wqCwG8c5yAg3AL1fm8T9AZtp/bbJGwl1pNrE7RuOX7PeMRUERVaPpEs+yqeoSmuOlokqw49pgomjLeh7icHNlG19yjs6XXOMedYm5xH2YxpV2tc0Ro2jJfxC50ApuxGob7lMsxfTbeUv07TyYxpeLucEH1gNd4IKH2LAg5TdVhlCafZvpskfncCfx8pOhJzd76bJWeYFnFciwcYfubRc12Ip/ppIhA1/mSZ/RxjFDrJC5xifFjJpY2Xl5zXdguFqYyTR1zSp1Y9p+tktDYYSNflcxI0iyO4TPBdlRcpeqjK/piF5bklq77VSEaA+z8qmJTFzIWiitbnzR794USKBUaT0NTEsVjZqLaFVqJoPN9ODG70IPbfBHKK+/q/AWR0tJzYHRULOa4MP+W/HfGadZUbfw177G7j/OGbIs8TahLyynl4X4RinF793Oz+BU0saXtUHrVBFT/DnA3ctNPoGbs4hRIjTok8i+algT1lTHi4SxFvONKNrgQFAq2/gFnWMXgwffgYMJpiKYkmW3tTg3ZQ9Jq+f8XN+A5eeUKHWvJWJ2sgJ1Sop+wwhqFVijqWaJhwtD8MNlSBeWNNWTa5Z5kPZw5+LbVT99wqTdx29lMUH4OIG/D86ruKEauBjvH5xy6um/Sfj7ei6UUVk4AIl3MyD4MSSTOFgSwsH/QJWaQ5as7ZcmgBZkzjjU1UrQ74ci1gWBCSGHtuV1H2mhSnO3Wp/3fEV5a+4wz//6qy8JxjZsmxxy5+4w9CDNJY09T072iKG0EnOS0arEYgXqYnXcYHwjTtUNAcMelOd4xpkoqiTYICWFq0JSiPfPDQdnt+4/wuqcXY47QILbgAAAABJRU5ErkJggg==);
}

.shadow {
  border-radius: 1px;
  box-shadow: 0 10px 30px rgba(0, 0, 0, 0.1), 0 1px 8px rgba(0, 0, 0, 0.2);
}
<main>
  <div class="acrylic shadow">Acrylic material!</div>
  <div class="acrylic shadow">Acrylic material!</div>
  <div class="acrylic shadow">Acrylic material!</div>
</main>
Pinard answered 16/6, 2017 at 8:20 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.