Vue3 + Vite 实现 SVG 图标组件自动加载
本文内容基于 AI 生成结果整理,可能包含不准确信息,仅供参考使用。
前言
在 Vue 项目开发中,SVG 图标因其清晰的矢量特性和良好的可定制性而被广泛使用。手动引入和注册每个图标不仅繁琐,还容易出错。本文将介绍如何在 Vue3 + Vite 项目中使用 vite-plugin-svg-icons
插件实现 SVG 图标组件的自动加载和全局注册,提高开发效率。
开发环境
本文基于以下环境版本实现:
- 操作系统: macOS
- Node.js: v22.17.0
- 包管理器: pnpm 10.13.1
- 编辑器: VSCode
- 构建工具: Vite 7.0.4
- SVG 插件: vite-plugin-svg-icons ^2.0.1
实现步骤
1. 安装插件
首先,使用 pnpm 安装 vite-plugin-svg-icons
插件:
bash
pnpm add vite-plugin-svg-icons -D
2. 配置 Vite
在 vite.config.ts
中添加插件配置:
ts
// vite.config.ts
import { defineConfig } from "vite";
import vue from "@vitejs/plugin-vue";
import { createSvgIconsPlugin } from "vite-plugin-svg-icons";
import path from "path";
// https://vite.dev/config/
export default defineConfig({
plugins: [
vue(),
// SVG 图标自动加载配置
createSvgIconsPlugin({
// 指定图标文件夹路径
iconDirs: [path.resolve(process.cwd(), "src/assets/icons")],
// 指定图标 ID 的格式
symbolId: "icon-[dir]-[name]",
}),
],
resolve: {
alias: {
"@": path.resolve(__dirname, "./src"),
},
},
});
3. 创建 SVG 图标组件
在 src/components/SvgIcon
目录下创建 index.vue
文件,实现可复用的 SVG 图标组件:
vue
// src/components/SvgIcon/index.vue
<template>
<!-- svg: 图标外层容器节点,内部需要与 use 标签结合使用 -->
<svg :style="{ width, height }">
<!-- xlink:href 指定使用哪一个图标,属性值务必为 #icon-图标名字 -->
<!-- use 标签 fill 属性可以设置图标的颜色 -->
<use :xlink:href="prefix + name" :fill="color"></use>
</svg>
</template>
<script setup lang="ts">
defineProps({
// 属性值前缀
prefix: {
type: String,
default: "#icon-",
},
// 提供使用的图标名字
name: String,
// 接受父组件传递的颜色
color: {
type: String,
default: "",
},
// 接受父组件传递的宽度
width: {
type: String,
default: "16px",
},
// 接受父组件传递的高度
height: {
type: String,
default: "16px",
},
});
</script>
4. 组织 SVG 图标文件
在 src
目录下创建 icons
文件夹,并将 SVG 图标文件放入其中。可以根据图标类型创建子文件夹进行分类。
5. 全局注册组件
在 src/components
目录下创建 index.ts
文件,用于全局注册组件:
ts
// src/components/index.ts
import type { App } from "vue";
import SvgIcon from "@/components/SvgIcon/index.vue";
import Paginate from "@/components/Paginate/index.vue";
// 类型安全的注册函数
const registerGlobalComponents = (app: App) => {
const components = {
SvgIcon,
Paginate,
};
Object.entries(components).forEach(([name, component]) => {
app.component(name, component);
});
};
export default {
install: registerGlobalComponents,
};
6. 在 main.ts 中引入并使用
在 src/main.ts
中引入 SVG 图标注册脚本和全局组件:
ts
// src/main.ts
import { createApp } from "vue";
import App from "./App.vue";
// 引入 SVG 图标注册脚本
import "virtual:svg-icons-register";
// 引入自定义插件对象:注册整个项目全局组件
import globalComponents from "@/components";
const app = createApp(App);
// 安装自定义插件
app.use(globalComponents);
app.mount("#app");
使用方法
在项目的任何组件中,可以直接使用全局注册的 SvgIcon
组件:
vue
<template>
<div class="example">
<!-- 基础使用 -->
<SvgIcon name="common-user" />
<!-- 自定义颜色和大小 -->
<SvgIcon name="menu-home" color="#42b983" width="24px" height="24px" />
<!-- 使用不同目录下的图标 -->
<SvgIcon name="other-settings" />
</div>
</template>
注意
name
属性的值为图标文件的路径(不包含扩展名),格式为 [目录名]-[文件名]
,与 vite.config.ts
中配置的 symbolId
格式相对应。原理说明
vite-plugin-svg-icons
插件会在 Vite 构建过程中,自动扫描指定目录下的所有 SVG 文件- 插件将这些 SVG 文件转换为 Symbol 元素,并注入到页面的
body
中 - 我们创建的
SvgIcon
组件通过use
标签引用这些 Symbol 元素,实现图标显示 - 通过全局注册组件,我们可以在项目的任何地方直接使用
SvgIcon
组件
扩展与优化
- 动态导入图标:如果项目图标数量很多,可以考虑按需动态导入,减少初始加载体积
- 图标预览:可以使用插件提供的预览功能,在开发过程中方便查看所有图标
- 自定义图标处理:可以通过插件配置自定义 SVG 的处理方式,如压缩、优化等
- 类型定义:为图标名称添加类型定义,提供更好的 TypeScript 支持
总结
通过 vite-plugin-svg-icons
插件,我们可以轻松实现 SVG 图标组件的自动加载和全局注册,避免了手动引入图标的繁琐工作。这种方式不仅提高了开发效率,还使得图标管理更加清晰和规范。