1
0
mirror of https://github.com/tabler/tabler-icons.git synced 2025-08-11 16:44:13 +02:00

Enhance webfont build process to support additional stroke weights and corresponding styles (#1313)

This commit is contained in:
Paweł Kuna
2025-01-29 21:44:55 +01:00
committed by GitHub
parent 183fc904ab
commit d953ab8e07
3 changed files with 155 additions and 139 deletions

View File

@@ -8,14 +8,23 @@ import { execSync } from 'child_process'
const DIR = getPackageDir('icons-webfont') const DIR = getPackageDir('icons-webfont')
const strokes = {
200: 1,
300: 1.5,
400: 2,
}
const buildOutline = async () => { const buildOutline = async () => {
let filesList = {} let filesList = {}
const icons = getAllIcons(true) const icons = getAllIcons(true)
const compileOptions = getCompileOptions() const compileOptions = getCompileOptions()
for (const strokeName in strokes) {
const stroke = strokes[strokeName]
await asyncForEach(Object.entries(icons), async ([type, icons]) => { await asyncForEach(Object.entries(icons), async ([type, icons]) => {
fs.mkdirSync(resolve(DIR, `icons-outlined/${type}`), { recursive: true }) fs.mkdirSync(resolve(DIR, `icons-outlined/${strokeName}/${type}`), { recursive: true })
filesList[type] = [] filesList[type] = []
await asyncForEach(icons, async function ({ name, content, unicode }) { await asyncForEach(icons, async function ({ name, content, unicode }) {
@@ -24,7 +33,7 @@ const buildOutline = async () => {
if (compileOptions.includeIcons.length === 0 || compileOptions.includeIcons.indexOf(name) >= 0) { if (compileOptions.includeIcons.length === 0 || compileOptions.includeIcons.indexOf(name) >= 0) {
if (unicode) { if (unicode) {
console.log('Stroke for:', name, unicode) console.log(`Stroke ${strokeName} for:`, name, unicode)
let filename = `${name}.svg` let filename = `${name}.svg`
if (unicode) { if (unicode) {
@@ -37,16 +46,14 @@ const buildOutline = async () => {
.replace('width="24"', 'width="1000"') .replace('width="24"', 'width="1000"')
.replace('height="24"', 'height="1000"') .replace('height="24"', 'height="1000"')
if (compileOptions.strokeWidth) {
content = content content = content
.replace('stroke-width="2"', `stroke-width="${compileOptions.strokeWidth}"`) .replace('stroke-width="2"', `stroke-width="${stroke}"`)
}
const cachedFilename = `u${unicode.toUpperCase()}-${name}.svg`; const cachedFilename = `u${unicode.toUpperCase()}-${name}.svg`;
if (unicode && fs.existsSync(resolve(DIR, `icons-outlined/${type}/${cachedFilename}`))) { if (unicode && fs.existsSync(resolve(DIR, `icons-outlined/${strokeName}/${type}/${cachedFilename}`))) {
// Get content // Get content
let cachedContent = fs.readFileSync(resolve(DIR, `icons-outlined/${type}/${cachedFilename}`), 'utf-8') let cachedContent = fs.readFileSync(resolve(DIR, `icons-outlined/${strokeName}/${type}/${cachedFilename}`), 'utf-8')
// Get hash // Get hash
let cachedHash = ''; let cachedHash = '';
@@ -71,22 +78,22 @@ const buildOutline = async () => {
color: 'black' color: 'black'
}).then(outlined => { }).then(outlined => {
// Save file // Save file
fs.writeFileSync(resolve(DIR, `icons-outlined/${type}/${filename}`), outlined, 'utf-8') fs.writeFileSync(resolve(DIR, `icons-outlined/${strokeName}/${type}/${filename}`), outlined, 'utf-8')
// Fix outline // Fix outline
execSync(`fontforge -lang=py -script .build/fix-outline.py icons-outlined/${type}/${filename}`).toString() execSync(`fontforge -lang=py -script .build/fix-outline.py icons-outlined/${strokeName}/${type}/${filename}`).toString()
execSync(`svgo icons-outlined/${type}/${filename}`).toString() execSync(`svgo icons-outlined/${strokeName}/${type}/${filename}`).toString()
// Add hash // Add hash
const fixedFileContent = fs const fixedFileContent = fs
.readFileSync(resolve(DIR, `icons-outlined/${type}/${filename}`), 'utf-8') .readFileSync(resolve(DIR, `icons-outlined/${strokeName}/${type}/${filename}`), 'utf-8')
.replace(/\n/g, ' ') .replace(/\n/g, ' ')
.trim(), .trim(),
hashString = `<!--!cache:${crypto.createHash('sha1').update(fixedFileContent).digest("hex")}-->` hashString = `<!--!cache:${crypto.createHash('sha1').update(fixedFileContent).digest("hex")}-->`
// Save file // Save file
fs.writeFileSync( fs.writeFileSync(
resolve(DIR, `icons-outlined/${type}/${filename}`), resolve(DIR, `icons-outlined/${strokeName}/${type}/${filename}`),
fixedFileContent + hashString, fixedFileContent + hashString,
'utf-8' 'utf-8'
) )
@@ -98,33 +105,34 @@ const buildOutline = async () => {
// Remove old files // Remove old files
await asyncForEach(Object.entries(icons), async ([type, icons]) => { await asyncForEach(Object.entries(icons), async ([type, icons]) => {
const existedFiles = (await glob(resolve(DIR, `icons-outlined/${type}/*.svg`))).map(file => basename(file)) const existedFiles = (await glob(resolve(DIR, `icons-outlined/${strokeName}/${type}/*.svg`))).map(file => basename(file))
existedFiles.forEach(file => { existedFiles.forEach(file => {
if (filesList[type].indexOf(file) === -1) { if (filesList[type].indexOf(file) === -1) {
console.log('Remove:', file) console.log('Remove:', file)
fs.unlinkSync(resolve(DIR, `icons-outlined/${type}/${file}`)) fs.unlinkSync(resolve(DIR, `icons-outlined/${strokeName}/${type}/${file}`))
} }
}) })
}) })
// Copy icons from firs to all directory // Copy icons from firs to all directory
await asyncForEach(Object.entries(icons), async ([type, icons]) => { await asyncForEach(Object.entries(icons), async ([type, icons]) => {
fs.mkdirSync(resolve(DIR, `icons-outlined/all`), { recursive: true }) fs.mkdirSync(resolve(DIR, `icons-outlined/${strokeName}/all`), { recursive: true })
await asyncForEach(icons, async function ({ name, unicode }) { await asyncForEach(icons, async function ({ name, unicode }) {
const iconName = `u${unicode.toUpperCase()}-${name}` const iconName = `u${unicode.toUpperCase()}-${name}`
if (fs.existsSync(resolve(DIR, `icons-outlined/${type}/${iconName}.svg`))) { if (fs.existsSync(resolve(DIR, `icons-outlined/${strokeName}/${type}/${iconName}.svg`))) {
// Copy file // Copy file
console.log(`Copy ${iconName} to all directory`) console.log(`Copy ${iconName} to all directory`)
fs.copyFileSync( fs.copyFileSync(
resolve(DIR, `icons-outlined/${type}/${iconName}.svg`), resolve(DIR, `icons-outlined/${strokeName}/${type}/${iconName}.svg`),
resolve(DIR, `icons-outlined/all/${iconName}${type !== 'outline' ? `-${type}` : ''}.svg`) resolve(DIR, `icons-outlined/${strokeName}/all/${iconName}${type !== 'outline' ? `-${type}` : ''}.svg`)
) )
} }
}) })
}) })
}
console.log('Done') console.log('Done')
} }

View File

@@ -8,6 +8,12 @@ const p = getPackageJson()
const DIR = getPackageDir('icons-webfont') const DIR = getPackageDir('icons-webfont')
const fontHeight = 1000 const fontHeight = 1000
const strokes = {
200: 1,
300: 1.5,
400: 2,
}
const aliases = getAliases(true) const aliases = getAliases(true)
fs.mkdirSync(`${DIR}/dist/fonts`, { recursive: true }) fs.mkdirSync(`${DIR}/dist/fonts`, { recursive: true })
@@ -26,11 +32,12 @@ const getAlliasesFlat = () => {
return allAliases return allAliases
} }
for (const strokeName in strokes) {
asyncForEach(types, async type => { asyncForEach(types, async type => {
console.log(`Building webfont for ${type} icons`) console.log(`Building ${strokeName} webfont for ${type} icons`)
await webfont({ await webfont({
files: `icons-outlined/${type}/*.svg`, files: `icons-outlined/${strokeName}/${type}/*.svg`,
fontName: 'tabler-icons', fontName: 'tabler-icons',
prependUnicode: true, prependUnicode: true,
formats, formats,
@@ -42,7 +49,7 @@ asyncForEach(types, async type => {
}) })
.then((result) => { .then((result) => {
formats.forEach(format => { formats.forEach(format => {
fs.writeFileSync(`${DIR}/dist/fonts/tabler-icons${type !== 'all' ? `-${type}` : ''}.${format}`, result[format]) fs.writeFileSync(`${DIR}/dist/fonts/tabler-icons${strokeName !== "400" ? `-${strokeName}` : ''}${type !== 'all' ? `-${type}` : ''}.${format}`, result[format])
}) })
const glyphs = result.glyphsData const glyphs = result.glyphsData
@@ -52,8 +59,8 @@ asyncForEach(types, async type => {
}) })
const options = { const options = {
name: `Tabler Icons${type !== 'all' ? ` ${toPascalCase(type)}` : ''}`, name: `Tabler Icons ${strokeName}${type !== 'all' ? ` ${toPascalCase(type)}` : ''}`,
fileName: `tabler-icons${type !== 'all' ? `-${type}` : ''}`, fileName: `tabler-icons${strokeName !== "400" ? `-${strokeName}` : ''}${type !== 'all' ? `-${type}` : ''}`,
glyphs, glyphs,
v: p.version, v: p.version,
aliases: (type === 'all' ? getAlliasesFlat() : aliases[type]) || {} aliases: (type === 'all' ? getAlliasesFlat() : aliases[type]) || {}
@@ -62,14 +69,15 @@ asyncForEach(types, async type => {
//scss //scss
const compiled = template(fs.readFileSync(`${DIR}/.build/iconfont.scss`).toString()) const compiled = template(fs.readFileSync(`${DIR}/.build/iconfont.scss`).toString())
const resultSCSS = compiled(options) const resultSCSS = compiled(options)
fs.writeFileSync(`${DIR}/dist/tabler-icons${type !== 'all' ? `-${type}` : ''}.scss`, resultSCSS) fs.writeFileSync(`${DIR}/dist/tabler-icons${strokeName !== "400" ? `-${strokeName}` : ''}${type !== 'all' ? `-${type}` : ''}.scss`, resultSCSS)
//html //html
const compiledHtml = template(fs.readFileSync(`${DIR}/.build/iconfont.html`).toString()) const compiledHtml = template(fs.readFileSync(`${DIR}/.build/iconfont.html`).toString())
const resultHtml = compiledHtml(options) const resultHtml = compiledHtml(options)
fs.writeFileSync(`${DIR}/dist/tabler-icons${type !== 'all' ? `-${type}` : ''}.html`, resultHtml) fs.writeFileSync(`${DIR}/dist/tabler-icons${strokeName !== "400" ? `-${strokeName}` : ''}${type !== 'all' ? `-${type}` : ''}.html`, resultHtml)
}) })
.catch((error) => { .catch((error) => {
throw error; throw error;
}); });
}) })
}

View File

@@ -21,9 +21,9 @@
"build:outline": "node .build/build-outline.mjs", "build:outline": "node .build/build-outline.mjs",
"build:webfont": "rm -fd dist/fonts/* && node .build/build-webfont.mjs", "build:webfont": "rm -fd dist/fonts/* && node .build/build-webfont.mjs",
"build:css": "pnpm run build:css:outline && pnpm run build:css:filled && pnpm run build:css:all", "build:css": "pnpm run build:css:outline && pnpm run build:css:filled && pnpm run build:css:all",
"build:css:filled": "sass dist/tabler-icons-filled.scss dist/tabler-icons-filled.css --style expanded && sass dist/tabler-icons-filled.scss dist/tabler-icons-filled.min.css --style compressed", "build:css:filled": "sass dist/tabler-icons-filled.scss dist/tabler-icons-filled.css --style expanded && sass dist/tabler-icons-filled.scss dist/tabler-icons-filled.min.css --style compressed && sass dist/tabler-icons-200-filled.scss dist/tabler-icons-200-filled.css --style expanded && sass dist/tabler-icons-200-filled.scss dist/tabler-icons-200-filled.min.css --style compressed && sass dist/tabler-icons-300-filled.scss dist/tabler-icons-300-filled.css --style expanded && sass dist/tabler-icons-300-filled.scss dist/tabler-icons-300-filled.min.css --style compressed",
"build:css:outline": "sass dist/tabler-icons-outline.scss dist/tabler-icons-outline.css --style expanded && sass dist/tabler-icons-outline.scss dist/tabler-icons-outline.min.css --style compressed", "build:css:outline": "sass dist/tabler-icons-outline.scss dist/tabler-icons-outline.css --style expanded && sass dist/tabler-icons-outline.scss dist/tabler-icons-outline.min.css --style compressed && sass dist/tabler-icons-200-outline.scss dist/tabler-icons-200-outline.css --style expanded && sass dist/tabler-icons-200-outline.scss dist/tabler-icons-200-outline.min.css --style compressed && sass dist/tabler-icons-300-outline.scss dist/tabler-icons-300-outline.css --style expanded && sass dist/tabler-icons-300-outline.scss dist/tabler-icons-300-outline.min.css --style compressed",
"build:css:all": "sass dist/tabler-icons.scss dist/tabler-icons.css --style expanded && sass dist/tabler-icons.scss dist/tabler-icons.min.css --style compressed", "build:css:all": "sass dist/tabler-icons.scss dist/tabler-icons.css --style expanded && sass dist/tabler-icons.scss dist/tabler-icons.min.css --style compressed && sass dist/tabler-icons-200.scss dist/tabler-icons-200.css --style expanded && sass dist/tabler-icons-200.scss dist/tabler-icons-200.min.css --style compressed && sass dist/tabler-icons-300.scss dist/tabler-icons-300.css --style expanded && sass dist/tabler-icons-300.scss dist/tabler-icons-300.min.css --style compressed",
"clean": "rm -rf dist && rm -rf ./icons-outlined", "clean": "rm -rf dist && rm -rf ./icons-outlined",
"copy": "pnpm run copy:license", "copy": "pnpm run copy:license",
"copy:license": "cp ../../LICENSE ./LICENSE" "copy:license": "cp ../../LICENSE ./LICENSE"