iconfont渐变色实现方案总结

news2024/11/27 18:34:14

52a8832dc13cd750f0db3feb797baf3c.gif

iconfont是前端技术中重要的一环——它能够方便地沉淀大量设计资产,并通过组件化的方式高效地在各种场景复用。而单纯应用iconfont,只能支持到纯色渲染图标,越来越难以满足高品质视觉效果的诉求。本文结合实际工作业务场景,调研了两种常见渐变iconfont实现方案,并提供icon组件封装demo,与各位读者分享。

cceeebeea6ccd146e091d0b219e34789.png

背景

为在淘内打造家装本地化产品心智,设计同学近期对业务的主题样式做了升级,采用整体黑金色调替换了原有淘宝橙色设计。为了突出家装行业奢华质感,设计对背景、文字、图标等大量采用了白-金渐变色样式。

0f452c9b6bdcc82375262ceb6dbcda94.png

944821e10fd476ccbe85d407c6d79347.png

78d9991f31fb77b5abf70fb3651670a4.png

在众多页面、组件中,存在大量可复用的渐变色图标,本着DRY(Don't Repeat Yourself)的原则,我们当然不能每次都去切个图。于是封装了一套能够支持渐变色的iconfont组件,将调研过程以及实现思路在此分享一下。

89694a0e70d8ab232d059e851b673308.png

实现效果

通过本文的方式,我们最终沉淀了业务的Icon组件,通过简单的调用方式即可快速实现渐变色图标。

<Icon 
  type="star" 
  color="#D5B198"
/>


<Icon 
  type="star" 
  color="#D5B198"
  // 设置渐变色,在支持的场景自动渲染,不支持的场景降级为color指定的纯色
  gradientColor="linear-gradient(150deg, #FFFDFC 0%, #D5B198 100%)"
/>

实际渲染效果如下:

28024f21b64de91c4841241e21ca9450.png

b1b2fca81c365da013f477da2d95ced8.png

渐变实现方案

业务内使用的iconfont均为font-class形式,以下实现方案也都基于该方式。iconfont的渐变色方案,也自然演变为寻找字体渐变色的方案。下面介绍在实现过程中了解到两种实现字体渐变色的方案,供大家参考。

  background-clip

background-clip用来设置元素背景(背景色或背景图)的延伸范围,通常有三个取值:content-box 、padding-box 和border-box ,即分别延伸到盒子模型的content区域、padding区域和border区域。

实现文字的渐变,我们用到了该属性的第四个取值:text 。即将元素背景的延伸范围限制在其内部文字的范围内。换句话说,只有文字的下方有背景。但单纯指定这个还不够,我们都知道元素的内容都是展示在背景之上,而且文字都是有颜色的,所以单独使用该css属性不会有任何实质的视觉效果——背景色展示在文字下方,又被文字盖住了。为了让背景色透出来,我们还需要将文字颜色去掉,最简单的方法就是将他们的颜色指定为透明色。

所以,一个简单的demo可以这么写:

<div class="gradient-test">
  柴七TEST
</div>
.gradient-test {
  color: transparent;
  background-image: linear-gradient(45deg, blue, red);
  background-clip: text;
  // 下面这两行不是必要的属性,单纯为了让文字大一点便于查看效果
  font-size: 50px;
  font-weight: 700;
}

效果如下:

e836e8e11d5c90e2a294dfc479f7949c.jpeg

TIP:部分老版本浏览器对该属性的支持需要添加-webkit- 前缀。在生产应用中,为达到最大兼容性,最好同时声明-webkit-background-clip: text 和background-clip: text

81eb103c4098d99436712b9dc5af4018.png

  mix-blend-mode: darken

apple官网中,可以学习到另一种实现方案。使用css的属性mix-blend-mode 。

简单介绍下什么是“混合模式”:就是描述当前绘制的图像,如何与其下方的底色相作用的。在不设置的情况下,绘制的图像颜色会直接盖住底色。混合模式的可取值非常多,这里介绍的文字渐变色方案只用到了“变暗(darken)”这个混合模式,其他的不再一一介绍。

混合模式的“变暗”,就是对比当前要绘制的像素和其下方的像素,比较每个色彩通道(即R、G、B)的色值,取较小的作为最终结果。举个例子,我有一个红色(255,0,0)的像素,要绘制在蓝色(0,0,255)的背景上,当混合模式指定为变暗时,最终绘制结果为纯黑色(0,0,0),计算过程如下:

R = min(255, 0) = 0

G = min(0,0) = 0

B = min(0, 255) = 0

apple工程师巧妙利用了这一特性,其首选绘制了一个纯黑色背景+白色文字的元素作为整体的背景。白色的三个色彩通道均为最大值255,而黑色均为最小值0,那么当任何图像与这样的背景色做变暗混合时,白色部分的混合结果一定是该图像的原始像素,黑色部分一定是黑色。通过这样的方式,我们可以将文字下方的图案以文字的轮廓展示出来,也就可以支持到渐变iconfont。

假定像素(r, g, b)

对黑色部分R = min(r, 0) = 0;G = min(g,0) = 0;B = min(b, 0) = 0,最终展示(0,0,0),即黑色

对白色部分R = min(r, 255) = 0;G = min(g,255) = 0;B = min(b, 255) = (r,g,b),最终展示(r,g,b),即该像素本身

纯黑色背景+白色文字

上面铺一个iphone 14 pro的小黑紫渐变图

设置小黑紫图片

mix-blend-mode: darken

531d8d7066c1f171c317b17231cae2f2.png

fff56fe0580e27be017b838cf24e157a.png

92e228985a734f8f0497352a013edf22.png

这个方法充满了艺术感,但是也有局限性——最终混合得到的结果的容器区域一定是有纯黑背景色的,在一些活动页可能有较好的应用场景,但却不能用于iconfont——因为iconfont的要求一定是字体部分有颜色,其他部分为透明色。所以最终并没有采取该方案。

9db510d79c6636048d4ca7f03d73cecf.jpeg

react组件设计

前面提到,我们业务中使用的iconfont方案是font-class,即类似这样的使用方式:

<span class="ahome-icon-notice"></span>

其css实现简单可描述为如下代码:

.ahome-icon-notice::before {
  content: "notice对应的iconfont字符"
}

这其实天然是一个容器包含了文字的形式,使用background-clip方案,我们只需要对文字的容器进行样式定义即可。

  简单demo

const Icon: FC<IIconProps> = props => {
  const {
    type,
    gradientColor,
    ...restProps
  } = props;


  return (
    <span
      className={cs(
        className,
        'ahome-iconfont',
        `ahome-icon-${type}`,
        {
          'gradient-icon': !!gradientColor,
        }
      )}
      style={{
        backgroundImage: gradientColor
      }}
      {...restProps}
    />
  );
};

对应的css样式(省略掉了部分不重要的样式)

.ahome-iconfont.gradient-icon {
    -webkit-background-clip: text;
    background-clip: text;
    color: transparent;
}

  使用媒体查询优雅降级

单纯知道上面的实现方法还不够,要投入生产应用,还有一个事情要考虑:当运行环境不支持background-clip时,如何优雅降级?这里可以使用媒体查询。思路可以简单一句话概括:只有在支持background-clip的环境里,才设置文字颜色为透明;且在不支持该属性的环境里,将容器的background-image设为none。

@supports (background-clip: text) {
  .ahome-iconfont.gradient-icon {
    -webkit-background-clip: text;
    background-clip: text;
    color: transparent !important;
  }
}


@supports not (background-clip: text) {
  .ahome-iconfont.gradient-icon {
    background-image: none !important;
  }
}

62af80938a82a8c58c42f8fc6ee08367.jpeg

总结

iconfont本质是字符,所以寻找iconfont渐变色渲染的方案可以转化为寻找字符渐变色渲染的方案。通过css的backgroud-clip: text或者mix-blend-mode:darken属性都可以实现字符渐变色渲染,但是后者会导致容器区域存在黑色背景,不适合图标场景。最终在实际生产应用时,还需要根据自己的业务受众,考虑在较老环境中的优雅降级。

0275061dbeb1424ac29f2172b0e9afda.jpeg

团队介绍

我们是大淘宝技术-品牌行业前端团队,目前负责消费电子、家装家居、汽车、运动户外、快消的线上线下零售新模式的探索,面向淘内淘外,提供商家、门店、消费者最佳用户体验。团队在XR、3D、2D渲染引擎这些创新体验上有不错的沉淀,同时面向全栈领域团队探索了 Serverless 云端研发模式,在消费者前台,通过端智能等手段提升消费者效率,同样面向工程领域,在跨端、前端工程化、中后台微前端都有一些沉淀,如果你是一位充满想象的终端极客,欢迎你的加入,通过自己的技术想法去改变淘系品牌行业业务的终端表达。

¤ 拓展阅读 ¤

3DXR技术 | 终端技术 | 音视频技术

服务端技术 | 技术质量 | 数据算法

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/759689.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

大数据面试题:Kafka的消费者和消费者组有什么区别?为什么需要消费者组?

面试题来源&#xff1a; 《大数据面试题 V4.0》 大数据面试题V3.0&#xff0c;523道题&#xff0c;679页&#xff0c;46w字 可回答&#xff1a;1&#xff09;说下Kafka的消费者和消费者组&#xff0c;以及它们的作用是什么&#xff1f; 参考答案&#xff1a; 1、什么是消费…

C++ 测试框架 GoogleTest 初学者入门篇

开发者虽然主要负责工程里的开发任务&#xff0c;但是每个开发完毕的功能都是需要开发者自测通过的&#xff0c;所以经常会听到开发者提起单元测试的话题。那么今天我就带大伙一起来看看大名鼎鼎的谷歌 C 测试框架 GoogleTest. 简单介绍 来看看谷歌官方是怎么介绍这个框架的&am…

数据结构(王卓版)——线性表

数据的存储结构之线性表 1、线性表的定义和特点 线性表的顺序存储结构 总结&#xff1a;

免费音频转文字的软件有哪些?分享这几个给大家!

在今天的数字化时代&#xff0c;音频转文字变得越来越常见和重要。无论是为了记录会议内容、制作字幕&#xff0c;还是为了更方便地查找和检索音频信息&#xff0c;免费的音频转文字软件可以帮助你实现这一目标。以下是几个方法&#xff0c;可以帮助你将音频转换为文字。 方法…

23年进阶高级测试,性能测试超细详解(附面试题+答案)一篇打通

目录&#xff1a;导读 前言一、Python编程入门到精通二、接口自动化项目实战三、Web自动化项目实战四、App自动化项目实战五、一线大厂简历六、测试开发DevOps体系七、常用自动化测试工具八、JMeter性能测试九、总结&#xff08;尾部小惊喜&#xff09; 前言 用户视角&#xf…

从2050回顾2020,职业规划与技术路径(节选)补充

很多朋友问了其中一段&#xff1a; 文明的提升&#xff0c;源于机械/能源/信息/智能四大模式的转变。机械将自然力或人力更高效利用&#xff0c;如风车&#xff0c;能源以蒸汽机为代表开启工业革命&#xff0c;信息启动了互联网时代&#xff0c;智能将实现虚拟社区的主导模式。…

CS 144 Lab One

CS 144 Lab One 实验结构环境配置如何调试StreamReassembler 实现 对应课程视频: 【计算机网络】 斯坦福大学CS144课程 Lab 1 对应的PDF: Lab Checkpoint 1: stitching substrings into a byte stream 实验结构 这幅图完整的说明了CS144 这门实验的结构&#xff1a; 其中&am…

【C++】多线程编程三(std::mutexstd::mutex、std::lock_guard、std::unique_lock详解)

目录 一、线程间共享数据 1.数据共享和条件竞争 2.避免恶性条件竞争 二、用互斥量来保护共享数据 1. 互斥量机制 2.mutex头文件介绍 三、C中使用互斥量mutex 1. 互斥量mutex使用 2.mutex类成员函数 ① 构造函数 ② lock() ③ unlock() ④ try_lock() 四、使用std::…

本地服务器localhost:3000一直连接不上

1.检查使用端口3000的进程: 在Windows上,运行 netstat -ano | findstr :3000在Mac/Linux上,运行lsof -i :3000 这将列出当前使用端口3000的任何进程。您要终止这些进程以释放该端口。 2.检查防火墙规则: 确保您的防火墙允许连接到localhost:3000。在MacOS和Windows上,通常不…

vue2已有项目迁移vue3踩坑记录

升级部分所需package.json版本&#xff0c;如vue及相关ui 参考vue3项目升级 解决运行报错 configureWebpack: {// webpack pluginsplugins: [// Ignore all locale files of moment.js// new webpack.IgnorePlugin(/^\.\/locale$/, /moment$/), 修改为new webpack.IgnorePlug…

azkaban

访问地址 https://xxx.xxx.xxx.xx:8443/index启动azkaban cd /data/servers/azkaban/executor ./bin/start-exec.sh cd /data/servers/azkaban/server ./bin/start-web.sh修改访问数据库密码 cd /data/servers/azkaban/executor/confvim azkaban.propertiescd /data/servers…

电脑桌面远程连接?外网远程桌面连接内网服务器穿透设置

自己个人电脑远程桌面连接另台服务器时&#xff0c;就可以使用到远程连接的功能&#xff0c;如在公司网络管理员远程连接ERP服务器管理操作。 远程连接就是在远程连接另外一台计算机。当某台计算机开启了远程桌面连接功能后我们就可以在网络的另一端控制这台计算机了&#xff…

人工智能大语言模型微调技术:SFT 监督微调、LoRA 微调方法、P-tuning v2 微调方法、Freeze 监督微调方法

人工智能大语言模型微调技术&#xff1a;SFT 监督微调、LoRA 微调方法、P-tuning v2 微调方法、Freeze 监督微调方法 1.SFT 监督微调 1.1 SFT 监督微调基本概念 SFT&#xff08;Supervised Fine-Tuning&#xff09;监督微调是指在源数据集上预训练一个神经网络模型&#xff…

ORCA优化器浅析——ORCA core流程

DXL query messages is parsed and transformed to an in-memory logical expression tree that is copied-in to the MemoExploration 触发生成逻辑等价表达式的转换规则。探索阶段将新的群组表达式添加到现有组中&#xff0c;并可能创建新的组。Exploration results in addin…

Java性能优化-测试try-catch放在循环内和外的性能对比与业务区别

场景 Java中使用JMH(Java Microbenchmark Harness 微基准测试框架)进行性能测试和优化&#xff1a; Java中使用JMH(Java Microbenchmark Harness 微基准测试框架)进行性能测试和优化_霸道流氓气质的博客-CSDN博客 使用如上方式测试Java中try-catch放在循环内和循环外是否有性…

NiuBi!简单且匿名的密码喷洒工具

工具介绍 通过 Amazon AWS 直通代理启动密码喷洒/暴力破解&#xff0c;为每次身份验证尝试转移请求的 IP 地址。这会动态创建 FireProx API&#xff0c;以实现更规避的密码喷射。 关注【Hack分享吧】公众号&#xff0c;回复关键字【230525】获取下载链接 小心帐户锁定&#xf…

Java 设计模式——工厂方法模式

目录 1.案例分析2.简单工厂模式2.1.结构2.2.案例实现2.2.1.抽象产品2.2.2.具体产品2.2.3.具体工厂2.2.4.测试 2.3.优缺点2.4.扩展 3.✨工厂方法模式3.1.介绍3.1.结构3.2.案例实现3.2.1.抽象工厂3.2.2.具体工厂3.2.3.测试 3.3.优缺点3.4.应用场景 1.案例分析 【需求】设计一个咖…

python获取职教云信息

⭐作者介绍&#xff1a;大二本科网络工程专业在读&#xff0c;持续学习Java&#xff0c;努力输出优质文章 ⭐作者主页&#xff1a;逐梦苍穹 ⭐所属专栏&#xff1a;项目。 目录 1、需求1.1、推荐课程1.2、课程详情 2、思路分析2.1、推荐课程完整代码 2.2、课程详情找到JSON数据…

4.2.tensorRT基础(1)-第一个trt程序,实现模型编译的过程

目录 前言1. hello案例2. 补充知识总结 前言 杜老师推出的 tensorRT从零起步高性能部署 课程&#xff0c;之前有看过一遍&#xff0c;但是没有做笔记&#xff0c;很多东西也忘了。这次重新撸一遍&#xff0c;顺便记记笔记。 本次课程学习 tensorRT 基础-第一个 trt 程序&#x…

SlickGrid学习

options&#xff1a; 选项 设置 enableCellNavigation 启用单元格导航&#xff0c;可以点单元格 enableColumnReorder 启动拖拽列 example-colspan.html 跨列实例 AutoTooltips plugin 隐藏列文字时自动显现列标题全文 Checkbox row select column 增加选择列来选择行…