Vue3.x+element-plus+ts踩坑笔记
阅读原文时间:2023年07月08日阅读:6

闲聊

前段时间小颖在B站找了个学习vue3+TS的视频,自己尝试着搭建了一些基础代码,在实现功能的过程中遇到了一些问题,为了防止自己遗忘,写个随笔记录一下嘻嘻

项目代码

git地址:vue3.x-ts-element-plus--demo

踩坑集合:

起因是小颖在封装  axios 时,发现引入的  ElNotification 组件没有样式,表单提交时加载  ElLoading 组件有没有样式,后来通过面向百度解决了该问题,嘻嘻

解决方案一:

第一步:执行下面代码

npm i unplugin-element-plus -D

第二步:在 vue.config.js 改为

const { defineConfig } = require('@vue/cli-service')

const AutoImport = require('unplugin-auto-import/webpack')

const Components = require('unplugin-vue-components/webpack')

const { ElementPlusResolver } = require('unplugin-vue-components/resolvers')

module.exports = defineConfig({

  transpileDependencies: true,

  configureWebpack: {

    plugins: [

      AutoImport({

        resolvers: [ElementPlusResolver()],

      }),

      Components({

        resolvers: [ElementPlusResolver()],

      }),

      require('unplugin-element-plus/webpack')({

        // options

      }),

    ],

  },

})

解决方案二:

直接全局引入 element-plus

第一步:修改 main.ts

import { createApp } from 'vue'

import App from './App.vue'

import router from './router'

import store from './store'

import ElementPlus from 'element-plus'

import 'element-plus/es/components/button/style/css'

createApp(App).use(store).use(router).use(ElementPlus).mount('#app')

参考:记录-解决element-plus自动引入后ElLoading、ElMessage、ElNotification、ElMessageBox样式丢失的问题

起因是小颖在封装菜单组件时,要动态遍历菜单数据根据数据中的  icon 值,通过:

动态渲染各自的菜单图标,但是没有渲染出来,通过F12发现渲染出来的dom就不是图标组件的dom,而是这样的:

当前 menuInfo.icon 值为:setting

左侧菜单组件

因考虑到菜单可能不止两级可能会是多级的所以小颖将其封装成以下组件:

leftMenu.vue

subMenu.vue

解决方案一:

修改 main.ts

import { createApp } from 'vue'
import App from './App.vue'
import router from './router'
import store from './store'
import ElementPlus from 'element-plus'
import 'element-plus/es/components/button/style/css'
import * as Icons from '@element-plus/icons-vue'
const app = createApp(App)

Object.keys(Icons).forEach(key => {
app.component(key, Icons[key as keyof typeof Icons])
})
app.use(store)
app.use(router)
app.use(ElementPlus)
app.mount('#app')

解决方案二:

将 main.ts 改回原来的

import { createApp } from 'vue'
import App from './App.vue'
import router from './router'
import store from './store'
createApp(App).use(store).use(router).mount('#app')
//公共css
import './assets/css/index.scss'

将subMenu.vue组件的 js 代码改为

import { defineComponent } from "vue";
import {
Document,
Menu as IconMenu,
Location,
Setting,
Menu,
Grid,
} from "@element-plus/icons-vue";
import { useRouter } from "vue-router";
import { useStore } from "vuex";
export default defineComponent({
components: {
Document,
Menu,
Location,
Setting,
Grid,
},
props: {
menuInfo: {
type: Object,
default: () => {
return {
id: "",
parent_id: "",
m_name: "",
icon: "",
childs: [],
};
},
},
},
setup() {
//路由
const router = useRouter();
//vuex
const store = useStore();
const menuFun = (event: any, index: string) => {
setNav(event);
store.dispatch("setMenuActive", { menuActive: index });
if (event.url && event.url.length > 0) {
router.push({
path: event.url,
query: {},
});
}
};
const setNav = (item: any) => {
store.dispatch("setNav", { nav: item });
};
return {
menuFun,
};
},
});

参考哪里忘记了,第一种是面向百度的,第二种是小颖自己试出来的

来来来找到了,参考这里;vue3 动态加载el-icon图标

解决方案:

第一步:执行以下代码

npm install --save vuex-persist

第二步:在 store 下的 index.ts 中引入并使用

import VuexPersistence from "vuex-persist";//解决页面刷新vuex数据丢失

const vuexLocal = new VuexPersistence({
storage: window.localStorage
})
export default createStore({
state: {
},
getters: {
},
mutations: {
},
actions: {
},
modules: modules,
plugins: [vuexLocal.plugin]
})

更多方法参考:vuex页面刷新数据丢失问题的四种解决方式

比如小颖要实现在 store 下的 index.ts 中自动引入 store  下的 modules 中的所有 ts

解决方案:

将 index.ts 改为:

import { createStore } from 'vuex'
import VuexPersistence from "vuex-persist";//解决页面刷新vuex数据丢失
const modulesFiles = require.context('./modules', false, /\.ts$/)

// you do not need `import app from './modules/app'`
// it will auto require all vuex module from modules file
const modules = modulesFiles.keys().reduce((modules: any, modulePath) => {
// set './app.js' => 'app'
const moduleName = modulePath.replace(/^\.\/(.*)\.\w+$/, '$1')
const value = modulesFiles(modulePath)
modules[moduleName] = value.default
return modules
}, {})
const vuexLocal = new VuexPersistence({
storage: window.localStorage
})
export default createStore({
state: {
},
getters: {
},
mutations: {
},
actions: {
},
modules: modules,
plugins: [vuexLocal.plugin]
})

后面的坑等后面写了再继续补充,最近小颖在忙着弄接的私活所以也没继续看vue3了,等这段时间忙完继续搞,打工人···················