CSS之clip一些花里胡哨的东西

最近的我,有点才思枯竭的感觉🤯。其实就是拖延。

众所周知喜欢搞一些花里胡哨的东西。继上次的gradient & hue-rotate之后

今天我们引来了一个新的神级属性(自封)clip,ta~da~!

先来个简单的

可以看到这是一段文本,但是这个文本花里胡哨的

对,它是彩色的。

background-clip

秘密就在这个属性background-clip

<span className="textContainer"> text </span>
.textContainer {
  display: flex;
  justify-content: center;
  align-items: center;
  height: 300px;
  width: 300px;
  font-size: 60px;
  font-weight: bold;

  /* 看下面,秘密在这 */
  background: linear-gradient(to right, rgb(42, 177, 1), blue);
  background-clip: text;
  color: transparent;
}

可以看到首先我给了 background 一个渐变。

这里我最初犯了一个错误:

gradient系列属性是background-image的一种属性!

gradient系列属性是background-image的一种属性!

gradient系列属性是background-image的一种属性!

这个属性是干什么的?

那么我更喜欢从clip这个词说起。

那么background-clip要怎么理解呢?

其实这里的clip显然是一个名词。当然在这里直接翻译成背景-夹子多少有点 der。可以意译为背景-裁剪区域

它有 3 个属性。

当然还有另一种实现彩色字体的方法 - mask

CSS中的mask属性允许用户屏蔽或剪裁特定点的图像来实现,部分或完全隐藏某个元素的可见性。

通过添加一个伪元素来完成mask的半透明遮罩效果,这样我们就能得到其中一个颜色的渐变效果,然后再把文本原有的颜色与之相结合,就能达到渐变特效。如上图大概就是3层效果叠加在一起。

<span text="text" className="textContainer">
  text
</span>
.textContainer {
  /* text原有的颜色 */
  color: green;
}

.textContainer::before {
  content: attr(text);
  position: absolute;
  z-index: 10;
  /* 伪元素的颜色(渐变色的另一色) */
  color: blue; 
  /* 渐变透明的遮罩 */
  mask: linear-gradient(to left, green, transparent);
}

效果如下

clip-path

接下来引出第二个神奇的属性clip-path。这个属性个人认为比background-clip还要神奇一些。

The clip-path CSS property creates a clipping region that sets what part of an element should be shown. Parts that are inside the region are shown, while those outside are hidden.

上面这段话是mdnclip-path的定义。这次我们可以把clip-path翻译成裁剪路径了(233333)。规定了element要显示的范围,范围之外全部 be hidden

这个属性特别强大,我们最终可以做到将一块的内容裁剪成自己想要的任意形状。

涉及到两个概念:clipping path(裁剪路径) & clipping region(裁剪区域)

其实这两个概念非常好理解,

clipping path可以接受很多参数,分为几个大类型(常用的):

用clip-path制作一个YouTube的暂停/播放按钮动画

先看一下YouTube的暂停/播放按钮效果是什么样的。

首先我需要用clip-path画两个矩形。

<div className="buttonBody">
  <div className="rectangle1"></div>
  <div className="rectangle2"></div>
</div>
.rectangle1 {
  height: 200px;
  width: 75px;
  background: #ffffff;
  clip-path: polygon(0% 0%, 0% 100%, 70% 100%, 70% 0%);
  transition: clip-path 0.5s ease;
}

.rectangle2 {
  height: 200px;
  width: 75px;
  background: #ffffff;
  clip-path: polygon(0% 0%, 0% 100%, 70% 100%, 70% 0%);
  transition: clip-path 0.5s ease;
}

可以看到我在绘制矩形使用的是polygon()。他接受具体的点值或者百分比。大概原理如下图。

然后可以看到两个矩形在绘制时给的坐标点时一摸一样的,因为这个百分比是相对当前容器的宽度

然后我要让两个矩形分别动起来。

因为是demo我就不用click来触发事件而是用hover

先是左边的这个矩形的效果。

可以看出来变化的过程是左边变短。

.rectangle1:hover {
  clip-path: polygon(0% 0%, 0% 100%, 100% 75%, 100% 25%);
}

给出的4个点

但是看起来总觉得怪怪的,对比一下原版

可以看到这个矩形变形的同时是变宽了的。

.rectangle1:hover {
  clip-path: polygon(0% 0%, 0% 100%, 100% 75%, 100% 25%);
}

然后是第二个矩形的变形,他这次是变成一个三角形。

.rectangle2:hover {
  clip-path: polygon(0% 25%, 0% 75%, 100% 50%);
}

但是如果直接给出polygon()里的参数变为3个点,会导致过渡动画失效的问题。

所以这里给出一个骚操作, 可以把最后两个点坐标定义成一样的

.rectangle2 {
  clip-path: polygon(0% 25%, 0% 75%, 100% 50%, 100% 50%);
}

这样就可以了,当然,右边的变形也是带有宽度改变的。

最后把他俩合在一起。

然后把hover事件放在父元素。

<div className="buttonBody">
  <div className="rectangle1"></div>
  <div className="rectangle2"></div>
</div>
.rectangle1 {
  height: 200px;
  width: 75px;
  background: #ffffff;
  clip-path: polygon(0% 0%, 0% 100%, 70% 100%, 70% 0%);
  transition: clip-path 0.5s ease;
}

.buttonBody:hover .rectangle1 {
  clip-path: polygon(0% 0%, 0% 100%, 100% 75%, 100% 25%);
}



.rectangle2 {
  height: 200px;
  width: 75px;
  background: #ffffff;
  clip-path: polygon(30% 0%, 30% 100%, 100% 100%, 100% 0%);
  transition: clip-path 0.5s ease;
}

.buttonBody:hover .rectangle2 {
  clip-path: polygon(0% 25%, 0% 75%, 100% 50%, 100% 50%);
}

最终的效果

参考