ReactNative中iconfont使用詳解

以下Rn指代ReactNative

1.iconfont簡(jiǎn)介

  • 什么是iconfont
    iconfont顯示成圖形圖標(biāo)的字體,因?yàn)樽煮w是矢量化圖形简烘,具有分辨率無(wú)關(guān)的特性笑陈,在任何分辨率和ppi下面放刨,都可以做到完美縮放笛臣,不像傳統(tǒng)位圖如:png云稚,jpg一樣,放大后會(huì)有鋸齒或者模糊沈堡。
  • 為什么使用iconfont
    對(duì)比圖片大小來(lái)說(shuō)容量更小静陈,支持樣式修改(大小,顏色)诞丽,適應(yīng)多分辨率鲸拥,網(wǎng)上有很多現(xiàn)成的iconfont資源可以使用。
image.png

2.在Rn中使用iconfont

簡(jiǎn)單介紹完iconfont僧免,現(xiàn)在說(shuō)說(shuō)在Rn中整么用它刑赶。
這里推薦使用react-native-vector-icons
react-native-vector-icons會(huì)把字體文件轉(zhuǎn)換成相應(yīng)的iconSets在Rn供我們使用。

安裝react-native-vector-icons

npm i --save react-native-vector-icons

ios下配置

用xCode打開(kāi)項(xiàng)目目錄下的ios懂衩,為了管理字體角撞,我們新建一個(gè)fonts目錄,字體文件統(tǒng)一放在里面勃痴,把字體文件拖進(jìn)這個(gè)文件夾。會(huì)有彈框提示并且記得Add to targets選中當(dāng)前項(xiàng)目热康。

image.png

確保Build Phases的Copy Bundle REsources中有字體文件

image.png

接著修改info.plist沛申,在information Property List下新增Fonts provided by application,在Fonts provided by application下在增加字體文件姐军,到這里ios就配置好了铁材。

image.png

android配置

安卓下會(huì)從android/app/src/main/assets/fonts目錄讀取字體文件尖淘,所以我們需要把字體文件*.ttf放在這個(gè)目錄下,然后在android/app/build.gradle文件中按需增加下面的配置著觉。

//使用內(nèi)置的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
]

使用內(nèi)置的iconSets

import Icon from 'react-native-vector-icons/FontAwesome';
<Icon name='rocket' size={60} color="#4F8EF7" />

上面的方式引用的是react-native-vector-icons內(nèi)置的一種iconSets, 除了FontAwesome還有其他iconSets村生,可以到react-native-vector-icons查看

內(nèi)置的iconSets

雖然內(nèi)置了很多iconSets給我們使用,但往往我們做項(xiàng)目時(shí)一般都會(huì)使用自己的iconfont饼丘,整么使用自己的iconfont呢趁桃?我們看源碼

源碼分析
react-native-vector-icons/FontAwesome這個(gè)返回的是一個(gè)iconSets,簡(jiǎn)單理解這個(gè)iconSets是一個(gè)可以幫我們顯示字體圖標(biāo)的組件肄鸽。其中name對(duì)應(yīng)圖標(biāo)在glyphMap.json文件中對(duì)應(yīng)的key卫病。(看到這里,glyphMap.json是什么鬼典徘?蟀苛??)

看react-native-vector-icons/FontAwesome的源碼

/**
 * FontAwesome icon set component.
 * Usage: <FontAwesome name="icon-name" size={20} color="#4F8EF7" />
 */

import createIconSet from './lib/create-icon-set';
import glyphMap from './glyphmaps/FontAwesome.json';

const iconSet = createIconSet(glyphMap, 'FontAwesome', 'FontAwesome.ttf');

export default iconSet;

createIconSet(glyphMap, fontFamily, fontFile)
參數(shù)說(shuō)明:
glyphMap: json對(duì)象(key是圖標(biāo)的name, value是圖標(biāo)對(duì)應(yīng)的10進(jìn)制數(shù))
fontFamily: 字體庫(kù)對(duì)應(yīng)的fontFamily
fontFile:字體文件名稱(注意這里只聲明字體庫(kù)名稱逮诲,字體庫(kù)路徑分平臺(tái)配置)
看glyphMap對(duì)應(yīng)的glyphmaps/FontAwesome.json

{
  "glass": 61440,
  "music": 61441,
  "search": 61442,
  "envelope-o": 61443,
  "heart": 61444,
  "star": 61445,
}

總結(jié)一下:
就是根據(jù)字體文件(.ttf|.otf)和glyphMap.json創(chuàng)建對(duì)應(yīng)的IconSets帜平,所以要想使用自定義的iconfont我們需要準(zhǔn)備這兩樣?xùn)|西。

使用自定義的iconSets

看完上面的源碼分析梅鹦,我們開(kāi)始自定義iconSets裆甩,
先準(zhǔn)備一套iconfont,作者習(xí)慣使用阿里巴巴矢量圖標(biāo)庫(kù)帘瞭,這里就拿這個(gè)來(lái)作為??
選取你需要的圖標(biāo)淑掌,添加為一個(gè)項(xiàng)目,如下蝶念。

image.png

項(xiàng)目默認(rèn)的fontFamily為iconfont抛腕,還記得上面創(chuàng)建iconSets函數(shù)的第二個(gè)參數(shù)嗎,每次對(duì)應(yīng)的就是這個(gè)媒殉。
這里我修改一下担敌。

image.png
image.png

下載項(xiàng)目,里面的iconfont.ttf就是我們需要的iconfont了廷蓉。

image.png

回想一下全封,創(chuàng)建createIconSet需要的東西,還少了glyphMap桃犬,glyphMap整么來(lái)呢刹悴。看這里

image.png

其中e69b是圖標(biāo)對(duì)應(yīng)的16進(jìn)制unicode我們需要的是10進(jìn)制攒暇,所以把它轉(zhuǎn)換一下土匀, 下面使用的是js

parseInt("e69b", 16)
59035

每個(gè)圖標(biāo)都需要轉(zhuǎn)換一次很麻煩,所以基于阿里巴巴圖標(biāo)矢量庫(kù)下載的文件形用,我用js寫了一個(gè)生成json的工具類就轧。把剛下載下來(lái)的iconfont.css证杭,iconfont.json, genJson.js放在同一目錄。?node執(zhí)行g(shù)enJson.js妒御,所需要的json對(duì)象就被寫入iconfont.json中了解愤。

/*iconfont.css*/
...省略...
.ica {
  font-family:"ica" !important;
  font-size:16px;
  font-style:normal;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
}

.icon-all:before { content: "\e696"; }

.icon-back:before { content: "\e697"; }

.icon-cart:before { content: "\e698"; }

.icon-category:before { content: "\e699"; }

.icon-close:before { content: "\e69a"; }

.icon-comments:before { content: "\e69b"; }


/*genJson.js*/
const path = require('path');

const oldPath = path.resolve(__dirname, 'iconfont.css');
const newPath = path.resolve(__dirname, 'iconfont.json');

var gen = module.exports = function () {
    const readline = require('readline');
    const fs = require('fs');

    const fRead = fs.createReadStream(oldPath);
    const fWrite = fs.createWriteStream(newPath, {flags: 'w+', defaultEncoding: 'utf8'});

    const objReadLine = readline.createInterface({
        input: fRead
    });

    var ret = {};

    objReadLine.on('line', line => {
        line = line && line.trim();
        if( !line.includes(":before") || !line.includes("content") ) return;
        var keyMatch = line.match(/\.(.*?):/);
        var valueMatch = line.match(/content:.*?\\(.*?);/);
        var key = keyMatch && keyMatch[1];
        var value = valueMatch && valueMatch[1];
        value = parseInt(value, 16);
        key && value && (ret[key] = value);
    });

    objReadLine.on('close', () => {
        console.log('readline close');
        fWrite.write(JSON.stringify(ret), 'utf8');
    });
};

gen();

創(chuàng)建iconSets需要的東西都準(zhǔn)備好了,開(kāi)始創(chuàng)建吧乎莉。

/*iconfont.json*/
{
  "icon-comments":  59035,
  "icon-close": 59034
}
/*iconSets.js*/

import createIconSet from 'react-native-vector-icons/lib/create-icon-set';
import glyphMap from './assets/fonts/iconfont.json';

const iconSet = createIconSet(glyphMap, "ica", 'iconfont.ttf');

export default iconSet;

/* componet.js*/
...
import Icon from './iconSets';
<Icon name='icon-comments' size={60} color="#4F8EF7" />

運(yùn)行一下送讲,看字體顯示出來(lái)了

image.png

項(xiàng)目相關(guān)代碼放在github上了,請(qǐng)移步react-native-iconfont-demo

如果有幫到你梦鉴,請(qǐng)點(diǎn)個(gè)贊吧李茫。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市肥橙,隨后出現(xiàn)的幾起案子魄宏,更是在濱河造成了極大的恐慌,老刑警劉巖存筏,帶你破解...
    沈念sama閱讀 219,270評(píng)論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件宠互,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡椭坚,警方通過(guò)查閱死者的電腦和手機(jī)予跌,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,489評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)善茎,“玉大人券册,你說(shuō)我怎么就攤上這事〈寡模” “怎么了烁焙?”我有些...
    開(kāi)封第一講書人閱讀 165,630評(píng)論 0 356
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)耕赘。 經(jīng)常有香客問(wèn)我骄蝇,道長(zhǎng),這世上最難降的妖魔是什么操骡? 我笑而不...
    開(kāi)封第一講書人閱讀 58,906評(píng)論 1 295
  • 正文 為了忘掉前任九火,我火速辦了婚禮,結(jié)果婚禮上册招,老公的妹妹穿的比我還像新娘岔激。我一直安慰自己,他們只是感情好是掰,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,928評(píng)論 6 392
  • 文/花漫 我一把揭開(kāi)白布鹦倚。 她就那樣靜靜地躺著,像睡著了一般冀惭。 火紅的嫁衣襯著肌膚如雪震叙。 梳的紋絲不亂的頭發(fā)上,一...
    開(kāi)封第一講書人閱讀 51,718評(píng)論 1 305
  • 那天散休,我揣著相機(jī)與錄音媒楼,去河邊找鬼。 笑死戚丸,一個(gè)胖子當(dāng)著我的面吹牛划址,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播限府,決...
    沈念sama閱讀 40,442評(píng)論 3 420
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼夺颤,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來(lái)了胁勺?” 一聲冷哼從身側(cè)響起世澜,我...
    開(kāi)封第一講書人閱讀 39,345評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎署穗,沒(méi)想到半個(gè)月后寥裂,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,802評(píng)論 1 317
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡案疲,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,984評(píng)論 3 337
  • 正文 我和宋清朗相戀三年封恰,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片褐啡。...
    茶點(diǎn)故事閱讀 40,117評(píng)論 1 351
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡诺舔,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出备畦,到底是詐尸還是另有隱情低飒,我是刑警寧澤,帶...
    沈念sama閱讀 35,810評(píng)論 5 346
  • 正文 年R本政府宣布萍恕,位于F島的核電站逸嘀,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏允粤。R本人自食惡果不足惜崭倘,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,462評(píng)論 3 331
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望类垫。 院中可真熱鬧司光,春花似錦、人聲如沸悉患。這莊子的主人今日做“春日...
    開(kāi)封第一講書人閱讀 32,011評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)售躁。三九已至坞淮,卻和暖如春茴晋,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背回窘。 一陣腳步聲響...
    開(kāi)封第一講書人閱讀 33,139評(píng)論 1 272
  • 我被黑心中介騙來(lái)泰國(guó)打工诺擅, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人啡直。 一個(gè)月前我還...
    沈念sama閱讀 48,377評(píng)論 3 373
  • 正文 我出身青樓烁涌,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親酒觅。 傳聞我的和親對(duì)象是個(gè)殘疾皇子撮执,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,060評(píng)論 2 355

推薦閱讀更多精彩內(nèi)容