前言
最近在仙逆的时候,发现一个号神奇的功能,刚开始以为很简单,但是当我深入了解后发现,这个属性很不简单,在这里记录一个学习的过程。
简单的一个截图例子:
一、CSS mask 属性基础概念
mask 属性允许通过遮罩层或裁剪区域,隐藏元素的部分或全部可见区域。其本质是通过透明度映射来控制元素显示范围:遮罩层中白色区域(透明值为 1)显示元素内容,黑色区域(透明值为 0)隐藏内容,灰色区域则根据亮度比例半透明显示。
1.2 与 clip-path 的核心区别
| 特性 | mask 属性 | clip-path 属性 |
|---|---|---|
| 作用原理 | 基于透明度映射隐藏内容 | 基于路径裁剪显示区域 |
| 视觉效果 | 可实现半透明渐变遮罩 | 仅支持硬边缘裁剪 |
| 兼容性 | 需注意浏览器前缀(如 -webkit-mask) | 现代浏览器支持较好 |
二、mask 属性语法与核心属性详解
2.1 复合属性与简写语法
mask 是以下属性的简写形式,可通过单一属性快速配置多重效果:
css
mask: [mask-image] [mask-mode] [mask-repeat] [mask-position]
[mask-clip] [mask-origin] [mask-size] [mask-composite];
2.2 核心属性分拆解析
2.2 核心属性分拆解析
(1)mask-image:定义遮罩图像
-
位图 / 矢量图:
css
mask-image: url(mask.png); /* 位图遮罩 */ mask-image: url(masks.svg#star); /* SVG路径遮罩 */ -
渐变效果:
css
mask-image: linear-gradient(to bottom, black 50%, transparent 50%); mask-image: radial-gradient(circle, black 60%, transparent 60%); -
渐变与图像混合:
css
mask-image: linear-gradient(90deg, transparent, black), url(pattern.png);
(2)mask-mode:定义遮罩层类型
alpha:使用图像的透明度通道作为遮罩(默认值)。luminance:使用图像的亮度值作为遮罩(白色区域显示,黑色区域隐藏)。
(3)mask-size & mask-position:控制遮罩尺寸与位置
css
mask-size: 50% 50%; /* 遮罩尺寸为元素的50% */
mask-position: center; /* 遮罩居中 */
mask: url(mask.png) 20px 30px / 80% no-repeat; /* 简写组合 */
(4)mask-composite:定义多遮罩层混合模式
css
mask-composite: add; /* 叠加遮罩 */
mask-composite: exclude; /* 排除遮罩区域 */
三、基础案例:从静态遮罩到渐变效果
3.1 位图与 SVG 遮罩实战
html
预览
<div class="mask-demo">
<img src="target.jpg" alt="目标图像" />
</div>
<style>
.mask-demo {
width: 300px;
height: 200px;
-webkit-mask: url(star.svg) no-repeat center; /* 兼容webkit内核 */
mask: url(star.svg) no-repeat center;
}
</style>
效果说明:通过 SVG 路径(如星形)作为遮罩,图像将仅显示为星形区域。
3.2 渐变遮罩实现动态视觉效果
css
/* 从上到下渐隐效果 */
.gradient-mask {
background: url(bg.jpg);
mask: linear-gradient(to bottom, black 80%, transparent 100%);
}
/* 圆形径向渐变遮罩 */
.circle-mask {
mask: radial-gradient(circle at 50% 50%, black 70%, transparent 70%);
}
效果演示:渐变遮罩可实现元素内容的平滑过渡隐藏,常用于图片焦点突出或文本渐隐效果。 最基本,使用 mask 的方式是借助图片,类似这样:
mask: url(mask.png); /* 使用位图来做遮罩 */
mask: url(masks.svg#star); /* 使用 SVG 图形中的形状来做遮罩 */
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>css mask</title>
<style>
.mask1 {
width: 200px;
height: 200px;
mask: url(./w3.png) no-repeat 50% 50%;
}
img {
width: 300px;
height: 300px;
}
</style>
</head>
<body>
<div class="mask1">
<img src="logo.jpg" alt="" />
</div>
</body>
</html>
使用线性渐变和径向渐变为图像创建不同的遮罩层:
mask: linear-gradient(#000, transparent);
mask: radial-gradient(circle, black 50%, rgba(0, 0, 0, 0.5) 50%);
示例
.mask1 {
background: url(psc.jpg) no-repeat left left;
mask: linear-gradient(180deg, transparent, #000);
}
使用mask效果
通过上面的案例,了解mark基本用法。
四.使用mask实现人像防遮挡功能
了解了mask 的使用方法后,接下来,我们运用 mask,简单实现视频弹幕中,弹幕碰到人物,自动被隐藏过滤的例子。 首先,我简单的模拟了一个视频,以及一些基本的弹幕:
<!-- 背景 -->
<div class="video"> </div>
<!-- <div class="g-yasuo"></div> -->
<!-- 包裹所有弹幕的容器 -->
<div class="bulletChatAll">
<!-- 所有弹幕 -->
<div class="bulletChat">6666</div>
...
<div class="bulletChat">777</div>
</div>
</div>
接来,我来添加一个人物,并且用 animation 模拟了简单的运动,在运动的过程中,人物是被弹幕给遮挡住的。
我利用 mask 制作一个
radial-gradient ,使得人物附近为 transparent,并且根据人物运动的 animation,给 mask 的 mask-position 也添加上相同的 animation 即可。最终可以得到这样的效果:
.bulletChatAll {
position: absolute;
mask: radial-gradient(circle at 100px 100px, transparent 60px, #fff 80px, #fff 100%);
animation: mask 10s infinite alternate;
}
@keyframes mask {
100% {
mask-position: 85vw 0;
}
}
五.实际生产环境中的运用
上面只是一个demo,利用 mask 实现弹幕遮罩过滤的效果。但是实际情况比上述的场景复制的多,因为人物英雄的位置是不确定的,每一刻都在变化。所以在实际生产环境中,mask 图片的参数,其实是由后端实时对视频进行处理计算出来的,然后传给前端,前端再进行渲染。