博客 > 软件开发 > 桌面&移动开发 > React Native
# 在 React Native Elements 中集成 iconfont ## 前言 react-native-elements 实际上也是使用了 react-native-vector-icons 库, 只不过是在外围又套了一层整合式的封装. 所以除了最后一步外, 本教程也适用于只使用 react-native-vector-icons 的项目集成 iconfont. ## 准备 iconfont 资源 这个不用多说什么. 不过就是注意, 如果同时使用多个iconfont库, 那么改一下字体名再导出. ## iOS 添加字体资源 1. 打开Xcode, 新建目录`Fonts`, 将字体文件(.ttf)拖入其中. 选择拷贝资源、添加到目标构建中. 2. 这时工程`Build Phases`中的`Copy Bundle Resources`里应该已经有这个文件了, 没有要加上. 3. 在项目目录的`info.plist`中添加对应的字体文件键值. ## Android 添加字体资源 1. 将字体文件拷贝到`android/app/src/main/assets/fonts/`. 2. 然后在`android/app/build.gradle`中增加下面的配置: ``` //使用内置的iconSets apply from: "../../node_modules/react-native-vector-icons/fonts.gradle" //使用自定义iconSets project.ext.vectoricons = [ iconFontNames: [ 'iconfont.ttf'] // Name of the font files you want to copy ] ``` ## 建立 Icon 组件 react-native-vector-icons 提供了[建立自定义图标字体库的API](https://github.com/oblador/react-native-vector-icons#custom-fonts), 这里使用其中的`createIconSet`方法. 方法原型如下: ```ts function createIconSet( glyphMap:{ [iconName:string]:number }, fontFamily:string, fontFile:string ){} ``` 其中, `glyphMap`是一个由图标名和其unicode十进制数组成的键值对对象. 这里产生一个问题: 如何给iconfont的字体建立一份`glyphMap`呢? 探索发现iconfont导出的压缩包中含有一个`iconfont.json`文件, 里面直接就有图标名和unicode数据, 但数据格式有一些偏差, 需要重新做一下映射. 网上有一些使用`iconfont.css`进行处理的文章, 原理类似但比较复杂, 直接用`.json`文件方便了许多. 2021年可用的生成`glyphMap`的脚本如下: ```js const filePath = process.argv[2]; if (filePath === undefined) {process.exit(-1);} const fs = require('fs'); const jsonSrc = JSON.parse(fs.readFileSync(filePath)); let jsonDst = {}; jsonSrc.glyphs.forEach(({font_class, unicode_decimal}) => { jsonDst[font_class] = unicode_decimal; }); console.log(JSON.stringify(jsonDst)); ``` 把此脚本的输出保存为`glyphmap.json`, 接下来即可在项目中正式建立自己的图标组件了! 在全局位置新建一个`Iconfont.js`文件, 写入如下内容: ```jsx import createIconSet from 'react-native-vector-icons/lib/create-icon-set'; import glyphMap from '<PATH TO GLYPHMAP JSON>'; export const Iconfont = createIconSet(glyphMap, "iconfont", 'iconfont.ttf'); ``` 现在, **已经可以使用如下组件来绘制图标了**! ```xml <Iconfont name="aixin" size={60} color="#4F8EF7" /> ``` 注意, **每次更新iconfont后, 需要把字体重新拷入原生资源目录, 需要重新生成glyphMap**. 建议做成自动化脚本. ## 在 react-native-elements 中集成自定义图标 现在只差最后一步. 应当知道, react-native-elements 给我们封装了一个 `Icon` 组件, 统一管理所有的 react-native-vector-icons 图标字体库(本来是一套图标一个组件, 现在把“套”的概念整合到 `Icon` 组件的 `type` 属性里了). 最好把我们自己的图标也接入到它的统一管理中. 这里参照[文档](https://reactnativeelements.com/docs/icon#custom-icon-fonts)进行操作. 在`index.js`添加以下语句: ```js // registerCustomIconType('type', VectorIconComponent); registerCustomIconType('iconfont', Iconfont); ``` 这样就可以将所有图标整合使用了! ```xml <View> <Icon type="iconfont" name="aixin" /> <Icon type="antdesign" name="qq" /> </View> ``` ## 参考资料 <https://www.jianshu.com/p/c900f6a0797f>