Css单标签实现转转Logo

2023年 8月 13日 44.9k 0

转转品牌升级后更新了全新的Logo,今天我们用纯CSS来实现转转的新Logo,为了有一定的挑战性,这里我们只使用一个标签实现,将最大化的使用CSS能力完成Logo的绘制与动画效果。

新logo保留了原本logo里转转熊的轮廓,两个熊耳是两个卫星围绕熊头旋转,是“循环”的意思。中间倾斜的转转首字母“Z”,既像二手质检的印章,又像N——NEW的首字母,代表着全新的二手生活方式。

Css单标签实现转转Logo-1图片

以上是我们要还原的Logo效果动图,现阶段使用方式主要是gif和lottie SVG两种方式。因为我们的目的是使用单标签实现所有的功能点,对于一些细节部分有所取舍,并不是百分百还原,也并不代表使用CSS的成本和效果是最好的,仅表达CSS的强大能力。接下来分析我们要核心实现的功能点:

  • 开始动画时中心的大圆以及2个围绕的小圆都有放大的效果
  • 动画开始后2个小圆围绕中心的椭圆旋转
  • 字母 Z 由大变小覆盖在中心的椭圆
  • 字母 Z 出现时中心的椭圆由红色边框圆变成实心红色圆
  • 仔细观察这个字母 Z 并不是普通的字符

基于上述分析接下来开始核心的代码拆解实现,在开始前先定义一些变量方便后续使用:

:root {
  /* 主题色 */
  --mainColor: #ff483c;
  /* 字体颜色 */
  --fontColor: #fff;
  /* 字体宽度 */
  --zWidth: 260px;
  /* 中心椭圆宽高比 */
  --parentScaleY: 0.9;
  /* 子元素抵消比例 */
  --childScaleY: calc(1 / var(--parentScaleY))
}

2个小圆旋转动画

如果是围绕一个正圆的旋转那么实现就简单很多了,但是这里是一个椭圆,纯CSS应该怎么做呢?根据小编目前的了解大概有以下几种方式都可以实现,但是对应的效果有所区别:

  • 使用 transform-style: preserve-3d;开启3D模式,但是对应的小圆在旋转角度存在视角消失的情况,需要额外处理
  • 使用 cubic-bezier 贝塞尔曲线执行动画可以达到椭圆曲线的效果,但是存在动画开始停止不可控的情况
  • 使用 rotate 0-360deg旋转,对应子元素需要设置反向旋转来抵消父级的旋转带来的影响

对比各种情况最终使用第三个方案即可满足条件且实现成本较低,首先画出一个椭圆的边框效果,设置scaleY和border-radius将一个正方形变成椭圆形,核心代码如下:

width: 570px;
  aspect-ratio: 1;
  border-radius: 50%;
  border: 10px solid var(--mainColor);
  transform: scaleY(var(--parentScaleY));

Css单标签实现转转Logo-2图片

然后给这个大圆添加旋转的动画,将整体旋转360度,这时还没有添加其他的元素,所以界面没有变化。

@keyframes circle {
  0% {
    transform: scaleY(var(--parentScaleY)) rotate(0);
  }
  100% {
    transform: scaleY(var(--parentScaleY)) rotate(360deg);
  }
}

设置大圆的动画执行相关参数。

animation: circle 1s 1 cubic-bezier(.5,.08,.52,.93) forwards;

边框上面的两个圈基于伪元素实现,绘制一个圆并使用定位将小圆定位于大圆的顶部两端。然后设置动画,这里需要注意的是需要设置反向旋转来抵消父级的旋转。

@keyframes mini-circle {
  0%{
    transform: rotate(0deg) scaleY(var(--childScaleY));
  }
 100%{
    transform: rotate(-360deg) scaleY(var(--childScaleY));
  }
}

这里为了方便查看将椭圆的参数调大进行对比,可以看到设置抵消后的区别一个圆被压缩了另一个保持了正常的圆形:

Css单标签实现转转Logo-3图片

未设置抵消

Css单标签实现转转Logo-4图片

已设置抵消

这里为了更好的利用元素的使用,这里将两个圆的绘制进一步优化到一个伪元素中,核心使用径向渐变背景实现,在同一个 background 中绘制两个纯色圆形,两个圆除了绘制的位置不同其他都是一样。代码如下:

background: 
  radial-gradient(circle 65px at 31% 24.5%,var(--mainColor) 0% 100%, transparent),
  radial-gradient(circle 65px at 72% 24.5%, var(--mainColor) 0% 100%, transparent);

到此这部分的内容基本功能完成,实际效果如下:

Css单标签实现转转Logo-5图片

Z 字母

接下来使用另一个伪元素实现 Z 字母的效果,仔细观察 Z 字母的两个拐角都是锐角效果,并不是日常字母有拐角的效果。

Css单标签实现转转Logo-6图片

基于当前的样式我们可以用3段矩形拼接完成效果,上下各一段,中间一段增加旋转角度,但是只用一个伪元素如何绘制三个矩形呢,还是用到CSS渐变,这次需要用到linear-gradient线性渐变,顶部和底部正常从上往下绘制,中间的部分需要绘制线条的旋转角度,除开需要显示的颜色其他部分用#0000透明色,为了方便看效果对三个矩形更换了不同的颜色,代码如下:

background: 
  linear-gradient(#f00 25%, #0000 25%),
  linear-gradient(#0000 75%, #29eb9a 25%),
  linear-gradient(124deg, #0000 40%, #000 40% 60%, #0000 60%);

绘制的效果如下:

Css单标签实现转转Logo-7图片

可以看到目前的效果还不能满足需求,两端都出现了多余的部分,需要进一步优化将其隐藏。这时候需要用到background-size与background-position,通过background-size设置绘制内容的大小,通过设置background-position设置绘制内容的起点位置,因为设置了一定的空隙部分需要增加no-repeat不重复,增加以下代码:

background-size: 80% var(--w), 80% var(--w), 100% 100%;
background-position: 0 0, 100% 0;
background-repeat: no-repeat;

Css单标签实现转转Logo-8图片

此时基本符合预期的效果,但实际设计图左下角的锐角部分有超出正常矩形一部分。

Css单标签实现转转Logo-9图片

所以需要对刚刚设置的size和position部分改进,将第一个矩形左侧空出16px:

background-size: 74% var(--w), 80% var(--w), 100% 100%;
background-position: 16px 0, 100% 0;

因为空出了左侧一部分距离,导致整个内容不再是一个正方形,所以需要设置 scaleX 还原宽度将图像还原到正方形。

对于刚刚设置的background相关属性可以在代码层进一步优化,使用简写将代码合并到一行:

background:
  linear-gradient(var(--fontColor) 25%, #0000 25%) 16px 0 / 74% var(--zWidth) no-repeat,
  linear-gradient(#0000 75%, var(--fontColor) 25%) 100% 0 / 80% var(--zWidth) no-repeat,
  linear-gradient(124deg, #0000 40%, var(--fontColor) 40% 60%, #0000 60%) 0 0 / 100% 100% no-repeat;

然后继续给这个 Z 添加动画效果,默认设置 opacity: 0 隐藏,因为 Z 是小圆动画执行结束才出现的,所以还需增加动画的延迟执行时间,增加动画相关代码:

animation: z 0.3s 1s 1 ease-in-out forwards;
opacity: 0;

设置动画将内容从1.5倍缩小到正常并设置旋转角度,返抵消以及平移到Logo正中心。这里因为初始增加了1.5的放大所以设置返抵消相关参数有所不同,在设置scaleY的同时还设置了skew进一步还原尺寸。

@keyframes z {
  0% {
    transform: rotate(-45deg) scale(1.5) translate(0, -50%) skew(-13deg, 8deg);
    opacity: 1;
  }
  100% {
    transform: rotate(-42deg) scaleY(var(--childScaleY)) translate(-4%, -64%) skew(-13deg, 8deg);
    opacity: 1;
  }
}

完成后的 Z 字母动画效果:

Css单标签实现转转Logo-10图片

其他细节

开始动画时中心的椭圆以及2个围绕的小圆都有放大的效果,所以需要对前面动画关键帧的定义继续完善。

小圆部分执行动画的前10%也增加scale(0.5)。

@keyframes mini-circle {
  0%{
    transform: rotate(0) scale(0.5);
  }
  10%{
    transform: rotate(0) scaleY(var(--childScaleY));
  }
}

大圆执行动画的前10%部分增加scale(0.8)。大圆部分还有一个效果是字母 Z 出现的时候中心的椭圆由边框圆变成实心圆,所以是在动画结束前增加对背景色的变化,代码如下:

@keyframes circle {
  0% {
    transform: scale(0.8) rotate(0);
  }
  10% {
    transform: scaleY(var(--parentScaleY)) rotate(0);
  }
  80% {
    background-color: var(--fontColor);
  }
  100% {
    background-color: var(--mainColor);
    transform: scaleY(var(--parentScaleY)) rotate(360deg);
  }
}

最后

到此我们整个代码实现过程就结束了,基于一个标签实现了转转的Logo的绘制及动画效果。当然这只是对其主要的功能还原,如需完整还原细节还需要进一步优化。

CSS的确是足够强大且对很多复杂的图形效果都能实现,这里我们主要是使用渐变背景实现图案的绘制,除了渐变还可以使用CSS阴影也能达到类似的效果。使用CSS对比使用SVG或GIF在资源体积上有很大的提升,本次实现的Logo使用lottie的json需要100KB左右,使用GIF大约需要27KB左右,但是纯CSS实现仅1KB不到即可完成,但是对于较为复杂的场景对应的代码也提升了不少的复杂度,大家要根据实际的情况使用,

相关文章

JavaScript2024新功能:Object.groupBy、正则表达式v标志
PHP trim 函数对多字节字符的使用和限制
新函数 json_validate() 、randomizer 类扩展…20 个PHP 8.3 新特性全面解析
使用HTMX为WordPress增效:如何在不使用复杂框架的情况下增强平台功能
为React 19做准备:WordPress 6.6用户指南
如何删除WordPress中的所有评论

发布评论