今天要实现的效果如图所示,鼠标悬停是图片卡片会有3D翻转的效果,且动画过程中还带有发光的效果。类似这种3D悬停效果日常看到的比较多,但是今天实现的这个效果有以下几个亮点:
- 核心CSS代码不超过10行
- 没有额外的元素(只有
<img>
标签) - 没有伪元素
整个交互过程主要就两个功能点:
- 鼠标悬停时卡片3D翻转
- 鼠标悬停时发光的效果
卡片3D翻转
开启3D效果需要用到 perspective
属性,通过设置 perspective
属性,我们可以改变元素在三维空间中的表现方式,使其看起来更加逼真和立体化。该属性会创建一个视角,在这个视角下,距离视点近的元素看起来比距离视点远的元素更大。
开启了3D模式则需要使用 rotate3d
将元素进行3D变换,这里使用 transform
实现,可以将 perspective
和其他 transform
函数一起使用,使代码更加简洁易懂。这里实现卡片3D翻转的核心代码如下:
transform: perspective(400px) rotate3d(var(--r, 1, -1, 0), calc(var(--i, 1) * var(--a)));
perspective(400px)
将元素视图设置为离观察者 400
像素的位置。
rotate3d()
函数可以用来将一个元素按照指定方向旋转。它的四个参数分别是 x
轴、y
轴、z
轴和旋转角度。
在这里第一个参数 var(--r, 1, -1, 0)
,如果该变量未定义则使用默认值 1, -1, 0
。在这里并没有定义--r
,所以也是等同于就是设置了 1, -1, 0
。即表示元素将围绕 x
轴、y
轴发生不同的旋转方向,z
轴则不发生变化。
第二个参数 calc(var(--i, 1) * var(--a))
是一个计算式,表示实时计算元素旋转的角度。其中 --i
变量默认为 1
,这里我们定义了 --a
是 8deg
,所以最终旋转的角度是 8deg
。
当鼠标悬停时,我们只需要改变 --i
变量的值,即可使卡片产生3D的效果。这里我们设置悬停时的值是 -1
,所以最终卡片的旋转角度会在 8deg
和 -8deg
之间。
img:hover { --i: -1; }
最后再配合 transition: .4s
过渡动画,此时我们的卡片效果如下:
悬停发光效果
上面提到只使用img
标签也不使用伪元素,那么从图片上方一闪而过的光束是怎么实现的呢?
这里我们使用CSS 的 -webkit-mask
属性,用于实现遮罩效果。刚好可以满足这个需求点,核心使用的代码如下:
-webkit-mask: linear-gradient(135deg,#000c 40%,#000,#000c 60%) 100% 100%/250% 250%;
具体解析如下:
linear-gradient(135deg, #000c 40%, #000, #000c 60%)
:创建一个线性渐变,从左上角到右下角,依次经过黑色半透明、全黑和黑色半透明三个颜色阶段。其中,颜色值#000c
一个十六进制颜色代码表示黑色半透明,#000
表示全黑。100% 100%
:指定背景图像的偏移量,即将背景定位到容器的右下角。/250% 250%
:指定背景图像的大小,即将背景图像水平方向和垂直方向都扩大到容器宽高的 2.5 倍。
以上代码实现了一个线性渐变遮罩,覆盖在我们的图片元素上,同时通过偏移和大小设置,让遮罩铺满整个元素,并且向四周扩散。此时我们再增加鼠标悬停的代码:
img:hover { -webkit-mask-position: 0 0; }
当鼠标悬停时,将遮罩层的偏移量都设置为0,此时再配合 transition: .4s
过渡动画悬停时发光的效果就动起来啦。
在线预览
最后
看到这里是不是感觉挺简单的,核心代码就这么几行即实现了看似比较复杂的交互效果。感兴趣的可以自己尝试实现看看。
看完本文如果觉得有用,记得点个赞支持,收藏起来说不定哪天就用上啦~