vite 中我是如何封装 svg?

前言

使用vite4新建项目的时候,发现项目中的案例使用的svg图标是以组件形式引用的。如下图(vue项目的代码)。于是乎,直接封装一个组件,好像也挺好的。不知道大家是如何看法?

组件规划

svg地址可配置

src目录新建plugins/svgIcons.ts:

arduino 复制代码
/**
 * 配置图标属性
 * iconsConfig.xxx xxx 为图标名称
 * svg: 图标的svg值
 */
export const iconsConfig = {
  // times 为组件名称
  times: {// 这个为对象,就是想着以后可以拓展一些内容
    // 这个地址把svg的拷进去就对了
    svg: '<svg ...><path ...></svg>'
  },
  book:{
    svg: '<svg ...><path ... /></svg>'
  }
}
svg-icons组件

src/components目录下新建svg-icons.vue,以下是使用jsx语法。

xml 复制代码
<!-- 使用jsx 语法,新建项目时要选择这个插件 -->
<!-- 使用jsx 不能用 setup 语法,并且要用lang=jsx -->
<script lang="jsx">
import { defineComponent } from 'vue'
// 这边是将刚才配置的数据直接引入,如果当心性能问题,也可以修改为传入props
import { iconsConfig } from '@/plugins/svgIcons.ts'
​
export default defineComponent({
  name: 'svgIcon',
  props: {
    // 图标名称
    iconName: {
      required: true,
      type: String
    },
    // svg 宽度
    width: Number,
    // svg 高度
    height: Number,
    // 颜色
    fill: String
  },
  setup(props, ctx) {
​
    let { svg } = iconsConfig[props.iconName]
​
    // 修改宽度
    if(props.width){
      let isWidth = svg.indexOf('width')
      svg = isWidth === -1 ? 
            svg.replace(/<svg/, `<svg width=${props.width}`) : 
            svg.replace(/width=".*?"/, `width=${props.width}`) 
    }
    // 修改高度
    if(props.height){
      let isHeight = svg.indexOf('height')
      svg = isHeight === -1 ?
            svg.replace(/<svg/, `<svg height=${props.height}`) :
            svg.replace(/height=".*?"/, `height=${props.height}`)
    }
​
    // 修改颜色
    if(props.fill){
      let isFill = svg.indexOf('fill')
      svg = isFill === -1 ?
            svg.replace(/<svg/, `<svg fill=${props.fill}`) :
            svg.replace(/fill=".*?"/, `fill=${props.fill}`)
    }
​
    return () => <div v-html={ svg }></div>;
  },
})
</script>
组件引入

svg图标,暴露出四个属性:图标名称(必填)、宽度、高度、填充颜色。

xml 复制代码
<script setup lang="ts">
  import SvgIcon from '@/components/svg-icons/index.vue'
</script>
​
<template>
  <!-- 时钟 -->
  <svg-icon 
    iconName="times" 
    width="50" 
    height="50" 
    fill="red"
  >
  </svg-icon>
  <!-- vue 图标 -->
  <svg-icon iconName="book" width="50" height="50"></svg-icon>
</template>

效果展示

上面的图标如下图所示

相关推荐
超*25 分钟前
腾讯云产品推荐----域名的使用
前端·javascript·腾讯云
苹果电脑的鑫鑫1 小时前
uni-app使用watch监听数据,当数据变化时页面没有根据变化数据渲染解决方法
java·前端·uni-app
计算机学姐1 小时前
基于Python爬虫大屏可视化的个性化小说书籍推荐系统
开发语言·vue.js·后端·爬虫·python·mysql·django
customer081 小时前
【开源免费】基于SpringBoot+Vue.JS卫生健康系统(JAVA毕业设计)
java·vue.js·spring boot·后端·spring cloud·kafka·开源
小沐在学习1 小时前
第六章元素应用CSS
前端·css
竹秋…2 小时前
vue3+element-plus==> el-form输入响应式失效踩坑!!!!!!!!!!
javascript·vue.js·elementui
晨曦_子画2 小时前
将 HTML 转换为 JSX:JSX 和 JSX 规则
前端·javascript·html
破浪前行·吴2 小时前
【学习】【HTML】localStorage、sessionStorage、cookie
前端·学习·html
新中地GIS开发老师2 小时前
GIS开发到底能应用在哪些行业 ?
java·javascript·arcgis·前端框架·echarts
AntBlack2 小时前
这篇绝不是标题党 :太好用了 , 一天就能快速实现一个可创业小项目
前端·后端·python