71 lines
2.1 KiB
TypeScript
71 lines
2.1 KiB
TypeScript
|
|
// vite/vite-plugin-icon-dts.ts
|
|||
|
|
import fs from 'fs-extra';
|
|||
|
|
import glob from 'fast-glob';
|
|||
|
|
import path from 'path';
|
|||
|
|
import { useThrottleFn } from '@vueuse/core';
|
|||
|
|
import type { PluginOption } from 'vite';
|
|||
|
|
|
|||
|
|
// glob 默认只支持 / 作为路径分隔符,windows 下会出现问题
|
|||
|
|
const normalizePath = (_path: string) => _path.replace(/\\/g, '/');
|
|||
|
|
|
|||
|
|
interface IconDtsOptions {
|
|||
|
|
/** svg 图标文件的路径 */
|
|||
|
|
iconDirs: string;
|
|||
|
|
/** 输出的dts文件的路径 */
|
|||
|
|
dts: string;
|
|||
|
|
/** 监听变化的延迟时间 */
|
|||
|
|
delay: number;
|
|||
|
|
/** 接口名称 */
|
|||
|
|
interfaceName: string;
|
|||
|
|
}
|
|||
|
|
|
|||
|
|
const defualtOptions: IconDtsOptions = {
|
|||
|
|
iconDirs: 'src/icons/',
|
|||
|
|
dts: 'svg-icons.d.ts',
|
|||
|
|
delay: 200,
|
|||
|
|
interfaceName: 'BaseSvgIconPath',
|
|||
|
|
};
|
|||
|
|
|
|||
|
|
/**
|
|||
|
|
* svg 图标路径生成dts文件
|
|||
|
|
*/
|
|||
|
|
export function svgIconPathOption(options: Partial<IconDtsOptions> = {}): PluginOption {
|
|||
|
|
const finalOptions: IconDtsOptions = { ...defualtOptions, ...options };
|
|||
|
|
const { delay, interfaceName } = finalOptions;
|
|||
|
|
let { iconDirs, dts } = finalOptions;
|
|||
|
|
iconDirs = normalizePath(iconDirs);
|
|||
|
|
dts = normalizePath(dts);
|
|||
|
|
let watcher: fs.FSWatcher | undefined = undefined;
|
|||
|
|
return {
|
|||
|
|
name: 'svg-icons-dts',
|
|||
|
|
buildStart: () => {
|
|||
|
|
if (!fs.existsSync(iconDirs)) {
|
|||
|
|
console.error(`${iconDirs}不存在,请检查`);
|
|||
|
|
return;
|
|||
|
|
}
|
|||
|
|
const update = () => {
|
|||
|
|
let assets: string[] = glob.sync(`${iconDirs}/**/*.svg`, {});
|
|||
|
|
assets = assets.map((i: string) => i.replace(iconDirs, '').replace('.svg', '').replace(/\//g, '-').replace(/^-+/, ''));
|
|||
|
|
let output = `interface ${interfaceName} {\n`;
|
|||
|
|
assets.forEach((_item) => {
|
|||
|
|
output += ` '${_item}': string;\n`;
|
|||
|
|
});
|
|||
|
|
output += `}\n`;
|
|||
|
|
const base = path.dirname(dts);
|
|||
|
|
fs.ensureDirSync(base);
|
|||
|
|
fs.writeFileSync(dts, output);
|
|||
|
|
};
|
|||
|
|
|
|||
|
|
const debounceLogic = useThrottleFn(update, delay);
|
|||
|
|
// 监听到文件变化,就重新写一遍
|
|||
|
|
watcher = fs.watch(iconDirs, { recursive: true }, () => {
|
|||
|
|
debounceLogic();
|
|||
|
|
});
|
|||
|
|
update();
|
|||
|
|
},
|
|||
|
|
buildEnd: () => {
|
|||
|
|
watcher?.close();
|
|||
|
|
},
|
|||
|
|
};
|
|||
|
|
}
|