# filter 滤镜 + mask 遮罩+backdrop-filter + backface-visibility

TIP

从本节开始我们学习 CSS3 新特性 filter 相关内容

  • filter 滤镜
  • mask 遮罩层
  • backdrop-filter 元素背后区域滤镜效果
  • backface-visibility 元素背面朝向用户时,是否可见

# 一、filter 滤镜

TIP

  • CSS filter 属性将模糊或颜色偏移等图形效果应用于元素。滤镜通常用于调整图像、背景和边框的渲染。
  • CSS filter 属性的值有很多,下表列出的值是比较常用的,也是我们需要掌握的。
  • filter 属性的值不为 none 时,会创建自己的 层叠上下文 (opens new window)

了解更多 filter 相关属性值,查阅 MDN 官方文档 filter (opens new window)

属性值 描述
blur() 将高斯模糊应用于输入图像,就是将元素变得模糊
brightness() 用于调整图像的亮度
contrast() 用于调整图像的对比度
drop-shadow() 沿着图像的轮廓生成阴影效果。(要与 box-shadow 属性做区分)
grayscale() 将图像转换为灰度图
opacity() 调整图像的透明度。(与 opactiy 属性效果一致)

# 1、blur() 调整图像模糊度

TIP

blur() 函数用于将高斯模糊应用于输入图像,也就是设置元素的模糊度

语法

/* length 为长度值,比如 10px , 值越大,图像越模糊 */
filter: blur(length);

代码示例

<style>
  .box {
    width: 100px;
    height: 100px;
    background-color: red;
    /* 模糊度 */
    filter: blur(20px);
  }
</style>

<div class="box"></div>
模糊值 最终效果
blur(5px) image-20250523211112493
blur(20px) image-20250523211031955

# 1.1、实战应用:背景模糊效果

TIP

利用 filter: blurbackground-size 的结合来实现背景模糊效果

./images/tx2.jpg 对应图片

tx1

<style>
  body {
    margin: 0;
  }
  .header {
    width: 100%;
    height: 220px;
    background-color: #000;
    position: relative;
    /* overflow: hidden; */
  }
  .header::before {
    content: "";
    width: 100%;
    height: 100%;
    display: block;
    /*
        背景图地址  不重复  居中对齐  宽度120% 高度自动
        */
    background: url("./images/tx1.jpg") no-repeat center / 120%;
    /* 添加模糊效果 */
    filter: blur(60px);
  }
  .header .content {
    font-size: 50px;
    color: red;
    text-align: center;
    position: absolute;
    top: 0;
    left: 0;
  }
</style>

<div class="header">
  <div class="content">我是内容.....</div>
</div>

image-20220725164313144

# 2、brightness() 调整图像亮度

TIP

图像亮度(Brightness/Luminance)是指图像中光线强度的视觉感知量,是影响图像视觉效果的核心要素之一。 光线弱,看东西变暗的;光线强(亮),看东西太刺眼。

brightness() 函数用于调整图像的亮度。

  • 值为 0%0 将创建全黑图像;
  • 值为 100%1 会使输入保持不变。
  • 如果值大于 100% 将使图像更加明亮。

语法

filter: brightness(40%);
filter: brightness(0.4);

代码示例

<style>
  .box {
    width: 200px;
    height: 200px;
    background: url(./images/ms.jpg) center;
    /* 调整图片的亮度 */
    /* filter:brightness(0); */
    /* filter:brightness(0.5); */
    /* filter:brightness(1);  */
    filter: brightness(1.2);
  }
</style>
<div class="box"></div>
属性值 渲染效果
brightness(0) image-20250523213248577
brightness(0.5) image-20250523213314775
brightness(1) image-20250523213336392
brightness(1.2) image-20250523213354450

# 3、contrast() 调整图像对比度

TIP

图像对比度(Contrast)是指图像中最亮部分与最暗部分之间的差异程度,是影响图像视觉冲击力和信息传达效率的关键因素。

CSS contrast() 函数调整图像的对比度。

  • 值是 0%0 将使图像变灰;
  • 值是 100%1 ,则无影响;
  • 若值超过 100%1 将增强对比度。当值大到一定程度时,图像中颜色之间是没有模糊部分,颜色之间分界线非常明显

语法

filter: contrast(200%);
filter: contrast(2);

代码示例

<style>
  .box {
    width: 200px;
    height: 200px;
    background-color: khaki;
    background: linear-gradient(red, yellow);
    /* filter:contrast(0); */
    /* filter:contrast(0.5); */
    /* filter:contrast(1); */
    /* filter:contrast(5); */
    filter: contrast(50);
    margin: 100px;
  }
</style>
<body>
  <div class="box box1"></div>
</body>
属性值 效果
contrast(0) image-20250523225555609
contrast(0.5) image-20250523225045818
contrast(1) image-20250523225141384
contrast(5) image-20250523225226341
contrast(50) image-20250523225259773

# 3.1、实战应用:文字交融展开动

GIF2025-04-2717-36-35

<style>
  body {
    margin: 0;
  }
  .container {
    height: 100px;
    width: 100%;
    background-color: #000;
    filter: contrast(40);
  }
  .text {
    font-size: 50px;
    color: #fff;
    font-weight: bold;
    line-height: 100px;
    text-align: center;
    /* 设置文字之间的间距 */
    /* letter-spacing: -50px; 汉字间间距 */
    /* filter: blur(10px); */
  }
  .animation-expand {
    animation: expand 1s ease-in both;
  }

  /* 展开动画 */
  @keyframes expand {
    0% {
      letter-spacing: -50px;
      filter: blur(10px);
    }

    100% {
      letter-spacing: 30px;
      filter: blur(0px);
    }
  }

  /* 动画执行结束后,将 container中的 filter 值设为 none */
  .filter-none {
    filter: none;
  }
</style>
<div class="container">
  <div class="text animation-expand">文字交融展开动画</div>
</div>
    <script>
      /* 获取 .conatiner 元素 */
      const container = document.querySelector(".container");
      /* 获取 .conatiner 元素 */
      const text = document.querySelector(".text");
      /* 给 text元素添加 animationend事件
       当animation动画结束后 给 container 元素添加 class类 filter-none
        */
      text.addEventListener("animationend", function () {
        container.classList.add("filter-none");
      });
    </script>

# 4、drop-shadow() 设置图像轮廓阴影

TIP

drop-shadow() 函数用于设置图像轮廓阴影,其用法与 box-shadow 属性类似,但有以下 4 个区别

  • drop-shadow 不支持内阴影
  • drop-shadow 属性在部分浏览器中,不支持设置阴影的扩散半径
  • drop-shadow 常用于设置图标不规则图形文字的阴影。box-shadow 更适合矩形盒子模型阴影的设置
  • drop-shadow 设置阴影实际上是是输入图像的 alpha 蒙版的一个模糊的、偏移的版本,用特定的颜色绘制并合成在图像下面,所以性能消耗比较大。而box-shadow 性能消耗较低
drop-shadow(水平偏移  垂直偏移  阴影模糊  阴影颜色 )
<style>
  .fi {
    filter: drop-shadow(0px 0px 8px #4444dd);
    /* box-shadow:0px 0px 8px #4444dd ; */
  }
</style>
<img src="./images/shape.png" width="200px" class="fi" />
阴影代码 渲染效果
filter: drop-shadow(0px 0px 8px #4444dd) image-20250523232251029
box-shadow:0px 0px 8px #4444dd image-20250523232317673

# 4.1、实战应用:带阴影的会话框

用到的三角形图片素材 arrow-left

image-20250620133937336

<style>
  .box {
    width: 200px;
    height: 200px;
    background-color: #cbebf8;
    border-radius: 10px;
    /* 阴影 */
    box-shadow: 0 0 5px #000;
    margin: 100px;
    position: relative; /* 相对定位 */
  }
  .box img {
    position: absolute;
    left: -34px;
    top: 50%;
    transform: translateY(-50%);
    /* 图片阴影 */
    filter: drop-shadow(0 0 3px #000);
  }
  .box::after {
    content: "";
    width: 50px;
    height: 50px;
    background-color: #cbebf8;
    display: block;
    /* 遮罩层 */
    position: absolute;
    left: 0px;
    top: 50%;
    transform: translateY(-50%);
  }
</style>

<div class="box">
  <img src="./images/arrow-left.png" alt="" />
</div>

# 5、grayscale() 将图像转为灰度图

TIP

grayscale() 函数用于将图像转换为灰度图。

  • 值为 0%0 则图像无变化。
  • 值为 100%1 则完全转为灰度图像
  • 值在 0%100% 之间,值越大,灰度越明显
<style>
  img {
    /* 正常无变化 
        filter: grayscale(0);*/
    /* 图片有一定灰度 
        filter: grayscale(0.5);*/
    /* 完全转换为灰度图像 */
    filter: grayscale(1);
  }
</style>
<img src="./images//ms.jpg" />
grayscale(0) grayscale(0.5) grayscale(1)
image-20250620134923250 image-20250620134901723 image-20250620134842199

# 5.1、实战应用:全站置灰(网站哀悼模式)

TIP

在一些特定的时间,为了哀悼某个特殊的人或事情,我们需要将全站首页内容置灰一天。

/* 将整个HTML文档转换为灰度图像 */
html {
  -webkit-filter: grayscale(
    100%
  ); /* 针对WebKit内核的浏览器,如Chrome和Safari */
  -moz-filter: grayscale(100%); /* 针对Mozilla Firefox */
  -ms-filter: grayscale(100%); /* 针对旧版本的Internet Explorer */
  -o-filter: grayscale(100%); /* 针对Opera浏览器 */

  filter: grayscale(100%); /* 标准的CSS滤镜属性 */
}
<style>
  html {
    /* 将整个HTML文档转换为灰度图像 */
    filter: grayscale(100%);
  }
  p {
    color: red;
  }
</style>
<div class="box">
  <img src="./images/ms.jpg" />
  <p>我是红色的,但现在是灰色的</p>
</div>
我是黑色的

image-20250620135821489

# 6、opacity() 调整图像透明度

TIP

opacity() 函数用法和 opacity 属性用法一样,都是用来调整元素的透明度。

两者的区别

有了 filter 滤镜,有些浏览器会针对filter:opacity() 提供硬件加速 (opens new window)以获取更好的性能表现。

<style>
  .box {
    width: 100px;
    height: 100px;
    background-color: skyblue;
    /* 0-1 从完全透明到不透明状态 */
    filter: opacity(0.5);
  }
</style>
<div class="box">
  <p>我是里面的内容</p>
</div>

image-20250620150937676

# 7、filter 滤镜多值写法

TIP

可以组合任意数量的函数来控制渲染。滤镜将按声明顺序依次应用。

/* 先模糊 再调整灰度 再调对比度 */
filter: blur(5px) grayscale(0.8) contrast(10);

# 7.1、实战应用:图像水墨画风格

<style>
  /* 水墨画风格:
    完全灰度 + 对比度 + 图像亮度调暗 + 轻微模糊 
    */
  .ink-wash {
    filter: grayscale(1) contrast(1.8) brightness(0.9) blur(0.3px);
  }
</style>
<img src="./images/hua.png" class="ink-wash" />
原图效果 调整为水墨画风格后效果
image-20250524003041069 image-20250524003005293

# 二、mask 遮罩

TIP

自 2023 年 12 月起,该功能适用于最新的设备和浏览器版本(浏览器兼容性如下表)

image-20250620162749690

注:

CSS Mask(遮罩)允许你使用图像渐变作为遮罩层来控制元素的可见性。遮罩层

  • 完全透明的部分,元素完全不可见
  • 半透明的部分,元素半透明状态
  • 不透明的部分,元素完全可见

CSS Mask 提供了一系列属性来精确控制遮罩效果,包括遮罩图像、位置、大小、重复方式等。以下是相关属性列表

属性 说明
mask-image 指定遮罩层图像或渐变
mask-mode 指定遮罩图像模式
mask-repeat 指定遮罩图像重复度
mask-position 指定遮罩图像位置
mask-size 指定遮罩图像延大小
mask-clip 指定遮罩图像延伸区
mask-origin 指定遮罩图定位区域
mask-composite 指定遮罩图像如何合成操作
mask 遮罩图像复合写法

以上属性可以组合使用,创造出各种视觉效果,如图像裁剪、渐变过渡、复杂形状显示等。

以下是后面代码中需要用到的图片素材

star.png ms.jpg
star ms

# 1、mask-image 遮罩层图像或渐变

TIP

mask-image 属性指定用作元素遮罩的图像或渐变。

它可以接受以下三种值

属性值 说明
URL 值 通过url() 加载一张遮罩图像
CSS 渐变 通过 CSS 线型渐变 、径向渐变、锥形渐变等绘制遮罩渐变图像
none 取消遮罩效果

语法

/* 值为图片地址 */
mask-image: url("./images/star.png");
/* 值为CSS渐变 */
mask-image: linear-gradient(pink, transparent);
/* 值为 none 取消遮罩效果 */
mask-image: none;

# 1.1、使用图像作为遮罩层

TIP

使用图像作为遮罩层

  • 图像不透明部分,元素完全显示
  • 透明部分则完全不显示
  • 半透明部分,呈半透明显示
/* 值为图片地址 */
mask-image: url("./images/star.png");
<style>
  .mask {
    /* 添加兼容型前缀 */
    -webkit-mask-image: url("./images/star.png");
    /* 图片为上图提供的纯黑色的五角星,图片默认会水平垂直方向重复 */
    mask-image: url("./images/star.png");
  }
</style>
<img src="./images/ms.jpg" class="mask" />

说明:

这个例子使用了一个纯黑色的五角形图像作为遮罩层,则图片在五角星区域内可见。

因为遮罩图像默认可水平垂直方向重复,所以会看到如下图所示效果

image-20250524234803526

使用从不透明到完全透明的图片做为遮罩层 (以下是图片素材)

bg

<style>
  img {
    mask-image: url(./images/bg.png);
  }
</style>
<img src="./images/ms.jpg" alt="" />

最终呈现如下效果

image-20250620162457429

# 1.2、使用 CSS 渐变作为遮罩层

<style>
  .mask {
    /* 添加兼容型前缀 */
    /* 从上往下的径向渐变(从粉色到看不见) */
    -webkit-mask-image: linear-gradient(pink, transparent);
    mask-image: linear-gradient(pink, transparent);
  }
</style>
<img src="./images/ms.jpg" class="mask" />

说明:

这个例子使用了一个从上到下,从完全不透明到完全透明的渐变图像作为遮罩层。则图片呈现从上到下,从完全不透明到完全透明的效果

(如下图)

image-20250524215933860

# 2、mask-mode 指定遮罩模式

TIP

mask-mode 属性指定遮罩图像是作为亮度遮罩还是 alpha 遮罩。

它接受以下三种值

属性 说明
alpha 使用图像的 alpha 通道(透明度)作为遮罩依据(默认)。也就是图像不透明区元素可见,完全透明区元素不可见。适用于带透明度的遮罩图像,
luminance 使用图像的亮度(黑白亮度)值作为遮罩依据。适用于渐变或黑白像,也就是亮或白的区域使元素更可见,较暗或黑的区域使元素更透明
match-source 如果 mask-image 的值类型是<image>,掩码层图像的 alpha 值应用作掩码值
如果mask-image (opens new window)属性是<mask-source>类型,掩模层图像的亮度值会被作为掩模值。

# 2.1、alpha 透明度

TIP

  • 使用图像的 alpha 通道 (透明度)作为遮罩依据(默认)。也就是图像不透明区元素可见,完全透明区元素不可见。
  • 适用于 png (带透明度)、SVG 等遮罩图像
<style>
  .box {
    width: 200px;
    height: 200px;
    background-color: khaki;
  }
  .mask {
    /* 从上到下,黑色从完全可见到完全不可见的透明渐变 */
    mask-image: linear-gradient(#000, transparent);
    /* 默认值,写和不写效果都一样 */
    mask-mode: alpha; /* 完全部透明区可见,完全透明区不可见 */
  }
</style>
<div class="box mask"></div>

image-20250524231934823

# 2.2、luminance 亮度

TIP

  • 使用图像的亮度值作为遮罩依据。也就是亮(白) 的区域使元素更可见,较暗(黑) 的区域使元素更透明
  • 适用于渐变 或 黑白遮罩图像
<style>
  .box {
    width: 200px;
    height: 200px;
    background-color: khaki;
  }
  .mask {
    /* 从上到下,黑色到白色的渐变 */
    mask-image: linear-gradient(#000, #fff);
    mask-mode: luminance; /* 黑的部分不可见,白的部分可见 */
  }
</style>
<div class="box mask"></div>

image-20250524232330332

# 3、mask-repeat 遮罩图像重复

TIP

mask-repeat 属性定义遮罩图像是否以及如何重复,类似于background-repeat

<style>
  .box {
    width: 300px;
    height: 200px;
    border: 1px solid red;
  }
  .mask {
    /* 添加兼容型前缀 */
    -webkit-mask-image: url("./images/star.png");
    /* 图片为上图提供的纯黑色的五角星,图片默认会水平垂直方向重复 */
    mask-image: url("./images/star.png");
    /* 可以将以下值修改为  repeat-x repeat-y no-repeat 查看不同效果*/
    mask-repeat: no-repeat;
  }
</style>
<div class="box">
  <img src="./images/ms.jpg" class="mask" />
</div>
mask-repeat 属性值 说明 渲染效果
repeat 默认值,水平和垂直两个方向重复 image-20250525131918052
repeat-x 水平方向重复 image-20250525132005724
repeat-y 垂直方向重复 image-20250525132045590
no-repeat 不重复 image-20250525132133353

# 4、mask-position 遮罩图像位置

TIP

mask-position 属性设置遮罩图像在元素内的初始位置,类似于background-position

<style>
  .box {
    width: 300px;
    height: 200px;
    border: 1px solid red;
  }
  .mask {
    /* 添加兼容型前缀 */
    -webkit-mask-image: url("./images/star.png");
    /* 图片为上图提供的纯黑色的五角星,图片默认会水平垂直方向重复 */
    mask-image: url("./images/star.png");
    /* 遮罩图像不重复 */
    mask-repeat: no-repeat;
    /* 遮罩图像位置*/
    mask-position: 50px 0px;
  }
</style>
<div class="box">
  <img src="./images/ms.jpg" class="mask" />
</div>
mask-position 属性值 说明 渲染效果
50px 0px 遮罩图像位于元素左上角水平 50px,垂直 0px 的位置 image-20250525131114983
left center 遮罩图像位于元素左侧中间 image-20250525130710320
center 遮罩图像位于元素中间 image-20250525130843657
100% 100% 遮罩图像位于元素右下角(right bottom) image-20250525130930622

# 5、mask-size 遮罩层图像大小

TIP

mask-size 属性指定遮罩图像的大小,类似于background-size

<style>
  .box {
    width: 300px;
    height: 200px;
    border: 1px solid red;
  }
  .mask {
    /* 添加兼容型前缀 */
    -webkit-mask-image: url("./images/star.png");
    /* 图片为上图提供的纯黑色的五角星 */
    mask-image: url("./images/star.png");
    mask-repeat: no-repeat; /* 遮罩图像重复度 */
    /* 遮罩层图像大小 */
    mask-size: 200px 200px;
  }
</style>
<div class="box">
  <img src="./images/ms.jpg" class="mask" />
</div>
mask-size 属性值 说明 渲染效果
300px 200px 遮罩图像宽 300px ,高 200px image-20250525134811458
300px auto 遮罩图像宽 300px 高自动等比缩放 image-20250525134920927
contain 遮罩图像等比缩放到正好完全填充到元素内 image-20250525135003627
cover 遮罩图像宽高等比缩放,正好完全覆盖掉元素(有部分可能会被裁剪) image-20250525135022451

# 6、mask-clip 遮罩图像延伸区域

TIP

mask-clip 属性指定遮罩图像的延伸区域,类似于background-clip

<style>
  .wrap {
    display: inline-block;
    border: 2px solid red;
  }
  .box {
    width: 200px; /* 内容宽 */
    height: 100px;
    border: 20px solid blue; /* 边框 */
    padding: 50px; /* 内边距 */
    background-color: khaki;
  }
  .mask {
    /* 添加兼容型前缀 */
    -webkit-mask-image: url("./images/star.png");
    /* 图片为上图提供的纯黑色的五角星 */
    mask-image: url("./images/star.png");
    /* mask-repeat:no-repeat;  遮罩图像重复度 */
    mask-position: 0 0; /* 遮罩层背景图居中 */
    mask-clip: border-box; /* 遮罩图像延伸区域 */
  }
</style>

<div class="wrap">
  <div class="box mask"></div>
</div>
mask-clip 属性值 说明 渲染效果
border-box 默认值。 遮罩效果会延伸到边框区域 image-20250525180154494
padding-box 遮罩效果会延伸到内边距区域 image-20250525180434151
content-box 遮罩效果只延伸到内容区域 image-20250525180513763

# 7、mask-origin 遮罩图像定位区域

TIP

mask-origin 属性指定遮罩图像的初始定位区域,类似于background-origin

<style>
  .wrap {
    display: inline-block;
    border: 2px solid red;
  }
  .box {
    width: 200px;
    height: 100px;
    border: 20px solid blue;
    padding: 50px;
    background-color: khaki;
  }
  .mask {
    /* 添加兼容型前缀 */
    -webkit-mask-image: url("./images/star.png");
    /* 图片为上图提供的纯黑色的五角星 */
    mask-image: url("./images/star.png");
    mask-repeat: no-repeat; /* 遮罩图像重复度 */
    mask-position: 0 0; /* 遮罩层背景图居中 */
    /* 遮罩图层初始定位区域 ,
        决定了mask-position设置的坐标相对于那个区域定位
        */
    mask-origin: padding-box;
  }
</style>

<div class="wrap">
  <div class="box mask"></div>
</div>
mask-origin 属性值 说明 渲染效果
border-box 默认值,遮罩图像初始定位区域为元素边框区域 image-20250525181729484
padding-box 遮罩图像初始定位区域为元素内边距区域 image-20250525181916029
content-box 遮罩图像初始定位区域为元素内容区 image-20250525181847964

# 8、多属性值写法

TIP

前面我们学过的 mask-imagemask-positionmask-size mask-repeat mask-clipmask-origin 属性都可以设置多组值,每组值之间用逗号分隔开来。

每个属性之间用逗号分隔的值,都是按顺序一一对应的,如果对应后面的值没有写,则以当前属性设置的第一组值为默认值显示。

<style>
  .wrap {
    display: inline-block;
    border: 2px solid red;
  }
  .mask {
    width: 300px;
    height: 200px;
    padding-top: 50px;
    /* 背景图片 */
    background-image: url("./images/ms.jpg");
    /* background-color: khaki; */
    /* background-image: url('./images/star.png') ,radial-gradient(50px at 150px 50px,red,red 100%,transparent); */
    /* 遮罩图像,第一个图像是一个五角星,第二个图像是一个半径为 50px的圆 */
    mask-image: url("./images/star.png"), radial-gradient(50px at 50%, red, red
          100%, transparent);
    /* 遮罩图像大小,第一个宽高为 50px,第二个宽高为 100px*/
    mask-size: 50px 50px, 100px 100px;
    /* 遮罩图像位置,两个图像位置坐标都是 0 0*/
    mask-position: 0 0;
    /* 遮罩图像重复度,第一个沿x轴重复,第二个沿 x 和 y 两个方向重复 */
    mask-repeat: repeat-x, repeat;
    /* 遮罩图像延伸区域 ,第一个延伸到边框区域,第二个延伸到内容区域 */
    mask-clip: border-box, content-box;
    /* 遮罩图像定位区域 ,第一个定位区域为边框区域,第二个定位区域为内容区域 */
    mask-origin: border-box, content-box;
  }
</style>
<div class="wrap">
  <div class="mask"></div>
</div>

image-20250525193901833

# 9、mask-composite 遮罩图像如何合成操作

TIP

CSS (opens new window) 属性 mask-composite 属性指定多个遮罩图像如何组合在一起。

以下表格中列出的所有组合模式

属性值 说明
add 将多个遮罩图像相加,显示他们的并集(显示区域并集)
subtract 显示上层遮罩图像有,而下层遮罩图像没有的部分
intersect 显示所有遮罩图像重叠的部分(显示区交集)
exclude 显示所有遮罩图像不重叠的区域

注意:

遮罩图像在组合时,是按 mask-image 后面值的书写顺序从后往前来组合的。

写在前面的叫上层,写在后面的叫下层

<style>
  .wrap {
    display: inline-block;
    border: 2px solid red;
  }
  .mask {
    width: 200px;
    height: 100px;
    /* 背景图片 */
    background-image: url("./images/ms.jpg");
    /* background-image: radial-gradient(50px at 50px 50px,red,red 100%,transparent), 
        radial-gradient(50px at 100px 50px,blue,blue 100%,transparent),
        radial-gradient(50px at 150px 50px,green,green 100%,transparent); */
    mask-image: radial-gradient(50px at 50px 50px, red, red 100%, transparent),
      radial-gradient(50px at 100px 50px, blue, blue 100%, transparent),
      radial-gradient(50px at 150px 50px, green, green 100%, transparent);
    /* 遮罩图合成操作 */
    mask-composite: add;
  }
</style>

<div class="wrap">
  <div class="mask"></div>
</div>
属性值 渲染效果
add image-20250525200505391
subtract image-20250525200832517
intersect(交叉) image-20250525201850865
exclude image-20250525201315228

# 10、mask 遮罩复合写法

TIP

CSS mask 属性为mask-imagemask-positionmask-sizemask-repeatmask-clipmask-originmask-composit 这些属性的简写。

语法

mask: mask-image mask-position/mask-size mask-repeat mask-clip mask-origin
  mask-composit;

代码示例

<style>
  .layout {
    display: inline-block;
    background-color: skyblue;
  }
  .mask {
    width: 300px;
    height: 200px;
    background-image: url("./images/star.png");
    mask: url("./images/star.png") no-repeat center/100px 100px;
  }
</style>

<div class="layout">
  <div class="mask">
    <img src="./images/ms.jpg" alt="" />
  </div>
</div>

image-20250620172703325

# 11、实战应用:实现元素倒影

image-20250601214748590

.box-reflect {
  width: 200px;
  height: 200px;
  position: relative; /* 相对定位 */
}
.box-reflect img {
  width: 100px;
  height: 100px;
  object-fit: cover;
  position: absolute; /* 绝对定位 */
  left: 0;
  top: 0;
}
.box-reflect img.reflect {
  top: 1px; /* 用来实现倒影与元素之间的间距 */
  transform-origin: bottom center;
  transform: rotateX(-180deg);
  /* 添加蒙版 */
  /* 因为图片旋转了180deg ,所以蒙版 方向也改变了*/
  mask: linear-gradient(to bottom, transparent, rgba(0, 0, 0, 0.8));
}
<div class="box-reflect">
  <img src="./caomei.png" />
  <img src="./caomei.png" class="reflect" />
</div>

# 12、实战应用:实现四角线框

GIF2025-4-218-43-51-17435906701854

以下代码用来实现上图动画中的 四角线框布局

<style>
  .box {
    width: 200px;
    height: 200px;
    border: 2px solid rgba(0, 0, 0, 0.5);
    margin: 10px;
    float: left;
  }
  .bg {
    background-image: linear-gradient(red, red), linear-gradient(red, red),
      linear-gradient(red, red), linear-gradient(red, red);
    background-size: 20px 20px;
    background-repeat: no-repeat;
    background-position: 0 0, 184px 0, 184px 184px, 0 184px;
    background-origin: border-box;
  }
  .mask {
    mask: linear-gradient(red, red), linear-gradient(red, red), linear-gradient(
        red,
        red
      ), linear-gradient(red, red);
    mask-size: 20px 20px;
    mask-repeat: no-repeat;
    mask-position: 0 0, 184px 0, 184px 184px, 0 184px;
    /* mask-origin: border-box; 
        默认值就是 border-box  */
  }

  .mask2 {
    /* background-image: conic-gradient(
        at 20px 20px,
        transparent 270deg,
        red 270deg
        ); 
        background-origin: border-box; */
    background-size: calc(100% - 20px) calc(100% - 20px);
    mask: conic-gradient(at 20px 20px, transparent 270deg, red 270deg);
    mask-size: calc(100% - 20px) calc(100% - 20px);
  }
</style>
<div class="box bg"></div>
<div class="box mask"></div>
<div class="box mask2"></div>

image-20250620180426792

# 13、实战应用:3D 立体文字

image-20250620182945195

<style>
  body {
    margin: 0;
  }
  .container {
    height: 250px;
    display: flex;
    align-items: center;
    justify-content: center;
    background-color: rgb(35, 152, 154);
  }
  .text {
    font-size: 150px;
    color: #fff;
    font-weight: bold;
    position: relative;
    z-index: 1; /* 创建自己的层叠上下 */
  }
  .text::after {
    content: "ICODING";
    position: absolute;
    left: 0;
    top: 0;
    color: #000;
    transform: translate(-77px, 22px) scaleY(0.6) skewX(50deg);
    /* 控制文字阴影在文字下面显示 */
    z-index: -1;
    /* 添加滤镜 */
    filter: blur(3px);
    /* 添加遮罩层 */
    mask: linear-gradient(transparent, #000);
  }
</style>

<div class="container">
  <div class="text">ICODING</div>
</div>

# 三、backdrop-filter 元素后面区域效果

TIP

backdrop-filter CSS (opens new window) 属性可以让你为一个元素后面区域添加图形效果(如模糊或颜色偏移)。

因为它适用于元素背后的所有元素,为了看到效果,必须使元素或其背景至少部分透明。

/* 
* backdrop-filter 属性用于为元素后面的区域添加图形效果
* 它会在元素背景(即"背后内容")上应用滤镜效果
* 类似于 filter 属性,但影响的是元素背后的内容而非元素本身
*/

/* 1. 关键字值 - 不应用任何滤镜效果 */
backdrop-filter: none;

/* 2. 使用SVG滤镜 
* 通过URL引用SVG文件中定义的滤镜
* 这里引用的是 common-filters.svg 文件中的 id="filter" 的滤镜
*/
backdrop-filter: url(common-filters.svg#filter);

/* 3. 滤镜函数值 - 各种内置滤镜效果 */

/* 高斯模糊效果 - 2像素半径的模糊 */
backdrop-filter: blur(2px);

/* 亮度调整 - 降低到原始亮度的60% */
backdrop-filter: brightness(60%);

/* 对比度调整 - 降低到原始对比度的40% */
backdrop-filter: contrast(40%);

/* 投影效果 - 右4px下4px的蓝色投影,10px模糊半径 */
backdrop-filter: drop-shadow(4px 4px 10px blue);

/* 灰度转换 - 30%程度的灰度效果 */
backdrop-filter: grayscale(30%);

/* 色相旋转 - 将颜色旋转120度 */
backdrop-filter: hue-rotate(120deg);

/* 颜色反转 - 70%程度的颜色反转 */
backdrop-filter: invert(70%);

/* 透明度调整 - 降低到20%不透明度 */
backdrop-filter: opacity(20%);

/* 深褐色调 - 90%程度的深褐色效果 */
backdrop-filter: sepia(90%);

/* 饱和度调整 - 增加到原始饱和度的80% */
backdrop-filter: saturate(80%);

/* 4. 多重滤镜组合 
* 可以组合多个滤镜效果,按顺序应用
* 这里先应用SVG滤镜,然后4px模糊,最后150%饱和度
*/
backdrop-filter: url(filters.svg#filter) blur(4px) saturate(150%);

/* 5. 全局值 - 标准的CSS全局关键字 */

/* 继承父元素的 backdrop-filter 值 */
backdrop-filter: inherit;

/* 重置为属性初始值(none) */
backdrop-filter: initial;

/* 回滚到浏览器或用户自定义的默认值 */
backdrop-filter: revert;

/* 回滚到上一层级的层值(CSS层叠上下文) */
backdrop-filter: revert-layer;

/* 取消任何滤镜效果(等同于 none) */
backdrop-filter: unset;

# 1、毛玻璃效果

<style>
  .box {
    width: 800px;
    height: 600px;
    position: relative;
  }
  .box img {
    width: 800px;
    height: 600px;
    object-fit: cover;
  }
  .box::after {
    content: "";
    position: absolute;
    /* 相当于 top right bottom left 的值都是 80px*/
    inset: 80px;
    background-color: rgba(255, 255, 255, 0.5);
    border-radius: 10px;
    /* 当前元素后面的图形添加模糊效果 */
    backdrop-filter: blur(10px);
    /* 亮度调整 - 降低到原始亮度的60% 
        backdrop-filter: brightness(60%);*/
    /* 对比度调整 - 提升对比度为原始的 200% 
        backdrop-filter: contrast(2);*/
  }
</style>
<div class="box">
  <img src="./images/16.png" />
</div>

image-20250620190713717

backdrop-filter 属性不同值效果

brightness(60%); contrast(2);
image-20250620191051886 image-20250620191229761

# 四、backface-visibility

TIP

CSS 属性 backface-visibility 指定当元素背面朝向观察者时是否可见。

属性值 说明
visible 元素背面朝向用户时可见
hidden 元素背面朝向用户时不可见
<style>
  .box {
    width: 200px;
    height: 200px;
    border: 2px solid red;
    margin: 100px;
    perspective: 800px;
  }
  .item {
    width: inherit;
    height: inherit;
    background-color: khaki;
    transform-origin: bottom center;
    transition: transform 2s;
    /* 背面朝向用户时不可见 */
    backface-visibility: hidden;
  }
  .box:hover .item {
    transform: rotateX(180deg);
  }
</style>
<div class="box">
  <div class="item"></div>
</div>

以上代码,当元素旋转到大于 90deg 时,则元素是背面朝向用户的。

hidden visible
GIF2025-6-2019-23-44 GIF2025-6-2019-23-02

# 五、专项训练案例(作业)

# 1、实战应用:可拖拽的环绕式照片墙(布局)

GIF2025-06-2318-32-20

静态布局版

<style>
  .ring {
    /* overflow: hidden; */
    /* width: 1400px; */
    width: 100%;
    margin: 200px auto;
    height: 600px;
    /* border: 5px solid red; */
    /* 设置透视距离,使3D效果更明显,模拟人站在离屏幕 900px的位置看物体 */
    perspective: 1000px;
    --length: 10; /* 确定展示图片的个数*/
  }

  .imgwrap {
    width: 400px;
    height: 400px;
    /* border: 2px solid blue; */
    margin: 0 auto;
    position: relative;
    /* 设置元素的子元素是位于 3D 空间中 */
    transform-style: preserve-3d;
  }

  .imgwrap img {
    width: 100%;
    height: 100%;
    /* 保持图片的宽高比,正好填充满容器 */
    object-fit: cover;
    position: absolute;
    /* 动态计算每个图片旋转的角度 =
        360deg / 总图片个数 * 每个图片对应的索引 
        */
    --angle: calc(360deg / var(--length) * var(--index));
    /* 对图片进行先旋转 再位移 */
    transform: rotateY(var(--angle)) translateZ(-700px);
    /* 元素背面朝向用户时不可见 */
    backface-visibility: hidden;
  }
</style>
<div class="ring">
  <div class="imgwrap">
    <img src="./images/01.png" style="--index:0" />
    <img src="./images/02.png" style="--index:1" />
    <img src="./images/03.png" style="--index:2" />
    <img src="./images/04.png" style="--index:3" />
    <img src="./images/05.png" style="--index:4" />
    <img src="./images/06.png" style="--index:5" />
    <img src="./images/07.png" style="--index:6" />
    <img src="./images/08.png" style="--index:7" />
    <img src="./images/09.png" style="--index:8" />
    <img src="./images/10.png" style="--index:9" />
  </div>
</div>

完整的 JS 版本

<style>
  body {
    /* background-color: #000; */
  }

  .ring {
    overflow: hidden;
    /* width: 1400px; */
    width: 100%;
    margin: 100px auto;
    height: 600px;
    /* border: 5px solid red; */
    /* 设置透视距离,使3D效果更明显,模拟人站在离屏幕 900px的位置看物体 */
    perspective: 1000px;
  }

  .imgwrap {
    width: 400px;
    height: 400px;
    /* border: 2px solid blue; */
    margin: 0 auto;
    position: relative;
    /* 设置元素的子元素是位于 3D 空间中 */
    transform-style: preserve-3d;
  }

  .imgwrap img {
    width: 100%;
    height: 100%;
    /* 保持图片的宽高比,正好填充满容器 */
    object-fit: cover;
    position: absolute;

    backface-visibility: hidden;
  }
</style>
<div class="ring">
  <div class="imgwrap">
    <img src="./images/01.png" />
    <img src="./images/02.png" />
    <img src="./images/03.png" />
    <img src="./images/04.png" />
    <img src="./images/05.png" />
    <img src="./images/06.png" />
    <img src="./images/07.png" />
    <img src="./images/08.png" />
    <img src="./images/09.png" />
    <img src="./images/10.png" />
  </div>
</div>
<script>
  // 获取所有图片
  let items = document.querySelectorAll(".ring img");
  // 得到图片的总个数
  const length = items.length;

  // 给每一个元素设置旋转的角度,让其围绕中心旋转一圈
  items.forEach((item, index) => {
    let angle = (360 / length) * index + "deg";
    item.style.transform = `rotateY(${angle}) translateZ(-700px)`;
  });

  // 环形元素的初始旋转角度
  let angle = 0;
  // 环形元素新的角度值
  let newAngle = 0;
  // 获取放置图片的容器
  let imgWrap = document.querySelector(".imgwrap");

  // 获取最外成容器
  let ring = document.querySelector(".ring");
  // 监听mousedown 事件
  ring.addEventListener("mousedown", function (e) {
    // 阻止默认行为
    e.preventDefault();
    // 记录鼠标按下时相对于浏览器可视区x的坐标
    let startX = e.clientX;

    // 监听 document 的 mousemove 事件
    document.addEventListener("mousemove", mousemoveHandler);
    function mousemoveHandler(e) {
      //鼠标移动时相对于*对于浏览器可视区 x 的坐标  endX
      let endX = e.clientX;
      // 计算鼠标移动的距离
      let moveX = endX - startX;
      // 圆的半径 700 ,计算圆的周长 2πr = 700 * Math.PI * 2
      const circumference = 2 * Math.PI * 700;
      // 计算环形元素的旋转角度
      newAngle = parseInt(angle - (moveX / circumference) * 360);
      // 设置环形元素的旋转角度
      imgWrap.style.transform = `rotateY(${newAngle}deg)`;
    }

    // 监听 document 的 mouseup 事件
    document.addEventListener("mouseup", mouseupHandler);
    function mouseupHandler(e) {
      // 更新角度值
      angle = newAngle;
      // 移除 mousemove 和 mouseup 的监听
      document.removeEventListener("mousemove", mousemoveHandler);
      document.removeEventListener("mouseup", mouseupHandler);
    }
  });
</script>

# 2、实战应用:3D 数字卡片翻转

GIF2025-6-2019-38-55

<style>
  .number-card {
    width: 200px;
    height: 200px;
    border: 2px solid #000;
    margin: 50px auto;
    position: relative;
    /* 设置透视距离,让卡片有3D效果 */
    perspective: 500px;
  }

  .number-card::before {
    content: "";
    display: block;
    width: 100%;
    height: 2px;
    background-color: #666;
    /* 分隔线相对父元素绝对定位在容器中间 */
    position: absolute;
    top: calc(50% - 1px);
    left: 0;
    /* 设置 z-index的值大一些,确保线条在所有卡片之上 */
    z-index: 99;
  }

  .card {
    width: 100%;
    height: 50%;
    background-color: #ddd;
    /*  省略部分css  ,具体见前面 .... */
    position: absolute;
    left: 0;
    top: 0;
    /* 字体大小 */
    font-size: 150px;
    /* 水平居中 */
    text-align: center;
    line-height: 200px;
    /* 将行高设为 200px ,这样文字垂直方向中心就对齐了容器中心 */
    overflow: hidden;
  }

  .card1-down {
    /* 向下移动50%的高度 */
    top: 50%;
    line-height: 0;
    /* 设置旋转的原点为顶部中心 */
    transform-origin: top center;
    /* 向止旋转 180deg */
    transform: rotateX(180deg);
    /* 元素背面朝向用户时,不可见 */
    backface-visibility: hidden;
    /* 添加过渡动画 */
    transition: transform 0.5s;
    z-index: 10;
  }

  /* 鼠标移入后效果 */
  .number-card:hover .card1-down {
    transform: rotateX(0deg);
  }

  .card2-up {
    /* 省略部分css ,具体见前面......*/
    /* 添加过渡动画 */
    transition: transform 0.5s;
    /* 旋转中心为 底部中心 */
    transform-origin: bottom center;
    backface-visibility: hidden;
  }

  .number-card:hover .card2-up {
    transform: rotateX(-180deg);
    /* x 轴反方向旋转 180deg */
  }

  .card2-down {
    /* 向下移动50%的高度 */
    top: 50%;
    line-height: 0;
  }
</style>
上次更新时间: 6/25/2025, 6:16:07 PM

大厂最新技术学习分享群

大厂最新技术学习分享群

微信扫一扫进群,获取资料

X