手把手教你Vue3?按需引入?Echarts的過(guò)程(收藏)
背景:新項(xiàng)目采用 Vue3 作為前端項(xiàng)目框架,避免不了要使用 echarts,但是在使用的時(shí)候,出現(xiàn)了與 Vue2 使用不一樣的地方,所以特別記下來(lái),希望給到有需要的同學(xué)一些幫助。
下載Echarts依賴(lài)
# 自己使用的yarn yarn add echarts # or npm install echarts --save # or # 有淘寶鏡像的可以選擇 (安裝速度快) cnpm install echarts --save
創(chuàng)建按需引入的配置文件 echarts.ts(文件名稱(chēng)自定義)及進(jìn)行配置
在你自己需要的目錄下創(chuàng)建引入 eachrts 配置的文件,我是在 src/utils 目錄下創(chuàng)建的 echarts.ts 文件(根據(jù)你自己的需求)在echarts.ts文件中引入echarts相關(guān)配置,網(wǎng)上有很多教程,但這里還是再啰嗦寫(xiě)一下,做戲做全套,一條龍服務(wù)。(看到最后有用給個(gè)點(diǎn)贊+收藏)
// 引入 echarts 核心模塊,核心模塊提供了 echarts 使用必須要的接口。
import * as echarts from "echarts/core";
/** 引入柱狀圖 + 折線圖 + 餅圖,圖表后綴都為 Chart,一般常用的就這三個(gè),如果還需要其他的,就自行添加 */
import { BarChart, LineChart, PieChart } from "echarts/charts";
// 引入提示框,標(biāo)題,直角坐標(biāo)系,數(shù)據(jù)集,內(nèi)置數(shù)據(jù)轉(zhuǎn)換器組件,組件后綴都為 Component
import {
TitleComponent,
TooltipComponent,
GridComponent,
DatasetComponent,
TransformComponent,
ToolboxComponent,
LegendComponent,
} from "echarts/components";
// 標(biāo)簽自動(dòng)布局,全局過(guò)渡動(dòng)畫(huà)等特性
import { LabelLayout, UniversalTransition } from "echarts/features";
// 引入 Canvas 渲染器,注意引入 CanvasRenderer 或者 SVGRenderer 是必須的一步
import { CanvasRenderer } from "echarts/renderers";
// 注冊(cè)必須的組件
echarts.use([
TitleComponent,
TooltipComponent,
GridComponent,
DatasetComponent,
TransformComponent,
ToolboxComponent,
LegendComponent,
LabelLayout,
UniversalTransition,
CanvasRenderer,
BarChart,
LineChart,
PieChart,
]);
// 導(dǎo)出
export default echarts;
根目錄 main.ts 文件引入創(chuàng)建的配置文件 echarts.ts
項(xiàng)目另外采用了 Pinia + ElementPlus + ElementPlus(圖標(biāo)),引入方式都在下面,希望能夠得到有需要的朋友幫助。
最重要的是要看本次引入echarts相關(guān)配置部分,注釋也寫(xiě)好了,大家可以參考一下。
import { createApp } from "vue";
import { createPinia } from "pinia";
// 引入Element-plus
import ElementPlus from "element-plus";
import "element-plus/dist/index.css";
import zhCn from "element-plus/dist/locale/zh-cn.mjs";
// 引入圖標(biāo)
import * as ElementPlusIconsVue from "@element-plus/icons-vue";
// 引入路由
import router from "./routes/index";
// 引入echarts
import echarts from "./utils/echarts";
// 引入整個(gè)項(xiàng)目入口文件
import App from "./App.vue";
// 定義全局樣式
import "./style.less";
// 創(chuàng)建 Store 實(shí)例
const piniaStore = createPinia();
// 創(chuàng)建Vue實(shí)例
const app = createApp(App);
// 注冊(cè) Element-plus圖標(biāo)
for (const [key, component] of Object.entries(ElementPlusIconsVue)) {
app.component(key, component);
}
/***********************echart 掛載 START*******************************/
// echarts 掛載到 Vue實(shí)例中
// 注意:app.config.globalProperties 和 app.provide('$echarts', echarts) 二選一即可
// Vue.prototype.$echarts = echarts; // vue2的掛載方式
app.config.globalProperties.$echarts = echarts; // vue3的掛載方式(一個(gè)用于注冊(cè)能夠被應(yīng)用內(nèi)所有組件實(shí)例訪問(wèn)到的全局屬性的對(duì)象。)
app.provide('$echarts', echarts); // vue3采用provide, inject方式使用
/***********************echart 掛載 END*******************************/
// 掛載element-plus,使用國(guó)際化,設(shè)置圖標(biāo)尺寸,及彈框?qū)蛹?jí)
app.use(router).use(piniaStore).use(ElementPlus, {
// size: 'small',
zIndex: 3000,
locale: zhCn,
});
// vue掛載到根節(jié)點(diǎn)
app.mount("#app");
組件內(nèi)使用echarts
前面基本都還簡(jiǎn)單,但是到了使用的時(shí)候,很多人就不知道怎么處理了,以前在 Vue2 的時(shí)候還可以通過(guò)vue實(shí)例 拿到 this 去使用,但是到了 Vue3 里面,沒(méi)有this 了,怎么辦?
不著急,辦法還是有的,并且還不止一種,請(qǐng)接著往下看。
1.通過(guò) getCurrentInstance() 獲取組件實(shí)例,類(lèi)似 Vue2 中的 this
<script setup lang="ts">
import { ref, getCurrentInstance } from 'vue';
// 獲取echart掛載的DOM節(jié)點(diǎn)
const container = ref();
// 獲取當(dāng)前組件實(shí)例
const { proxy }: any = getCurrentInstance();
// echarts初始化
let myChart = proxy.$echarts.init(container.value);
const option = {
// 自定義echarts圖標(biāo)相關(guān)配置
};
myChart.setOption(option);
// 根據(jù)頁(yè)面大小自動(dòng)響應(yīng)圖表大小
window.addEventListener("resize", function () {
myChart.resize();
});
</script>
<template>
<div id="echarts1" ref="container"></div>
</template>
2.通過(guò)采用provide, inject方式使用
<script setup lang="ts">
import { ref, inject} from 'vue';
// 獲取echart掛載的DOM節(jié)點(diǎn)
const container = ref();
// 通過(guò) inject 接收Echarts
const Echarts = inject('$echarts');
// echarts初始化
const myChart = (Echarts as any).init(container.value);
const option = {
// 自定義echarts圖標(biāo)相關(guān)配置
};
myChart.setOption(option);
// 根據(jù)頁(yè)面大小自動(dòng)響應(yīng)圖表大小
window.addEventListener("resize", function () {
myChart.resize();
});
</script>
<template>
<div id="echarts1" ref="container"></div>
</template>
上面的兩種方式唯一不同的就是如何獲取(接收)注冊(cè)echarts。
到這里就結(jié)束了嗎?
問(wèn)題解決
太天真了!
這里我就要問(wèn)下,上面兩種方式的代碼能夠跑起來(lái)嗎?
事實(shí)上,不行,因?yàn)樯厦?script 內(nèi)的代碼運(yùn)行的時(shí)候,還沒(méi)有掛載到組件實(shí)例上,找不到定義的 ref 對(duì)象 container,即使通過(guò)document.getElementById('echarts1') 的方式獲取DOM節(jié)點(diǎn) <div id="echarts1" ref="container"></div> 一樣報(bào) null 或者 undefined。
子任就會(huì)出現(xiàn)如下報(bào)錯(cuò):Uncaught (in promise) Error: Initialize failed: invalid dom.

不信? 那么就控制臺(tái)打印輸出看看兩種方式獲取的DOM到底是個(gè)啥。
<script setup lang="ts">
import { ref } from 'vue';
// 獲取echart掛載的DOM節(jié)點(diǎn)
const container = ref();
console.log('獲取的DOM-div:', document.getElementById('echarts1'), container.value);
</script>
<template>
<div id="echarts1" ref="container"></div>
</template>
上面的代碼輸出一下結(jié)果:

那么解決辦法也很簡(jiǎn)單,直接開(kāi)啟一個(gè)延時(shí)器 setTimeout 就好了。
最后完整代碼如下:
<script setup lang="ts">
import { ref, inject, onBeforeUnmount} from 'vue';
// 獲取echart掛載的DOM節(jié)點(diǎn)
const container = ref();
// 定義延時(shí)器指針對(duì)象,便于組件實(shí)例銷(xiāo)毀的時(shí)候以便清除
const timer = ref();
// 通過(guò) inject 接收Echarts
const Echarts = inject('$echarts');
// 或
// 通過(guò)Vue全局注冊(cè)方式獲取
// const {proxy}: any = getCurrentInstance();
const initEchartsOneFn = () => {
// echarts初始化
const myChart = (Echarts as any).init(container.value);
// 或
// let myChart = proxy.$echarts.init(container.value);
const option = {
// 自定義echarts圖標(biāo)相關(guān)配置
};
myChart.setOption(option);
// 根據(jù)頁(yè)面大小自動(dòng)響應(yīng)圖表大小
window.addEventListener("resize", function () {
myChart.resize();
});
}
// 判斷定時(shí)器是否存在
if (timer.value) {
clearTimeout(timer.value);
}
// 綁定定時(shí)器,銷(xiāo)毀的時(shí)候再次清除
timer.value = setTimeout(() => initEchartsOneFn(), 1000);
// 組件實(shí)例銷(xiāo)毀前清除延時(shí)器對(duì)象
onBeforeUnmount(() => {
if (timer.value) clearTimeout(timer.value);
});
</script>
// 此處部分將就著看看
<template>
<div id="echarts1" ref="container"></div>
</template>
以證清白,上效果圖:

最后
到此這篇關(guān)于Vue3 手把手按需引入 Echarts的文章就介紹到這了,更多相關(guān)Vue按需引入 Echarts內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Vue Element前端應(yīng)用開(kāi)發(fā)之前端API接口的封裝
對(duì)整個(gè)系統(tǒng)來(lái)說(shuō),一般會(huì)有很多業(yè)務(wù)對(duì)象,而每個(gè)業(yè)務(wù)對(duì)象的API接口又有很多。我們這個(gè)VUE+Element 前端應(yīng)用就是針對(duì)ABP框架的業(yè)務(wù)對(duì)象,因此前端的業(yè)務(wù)對(duì)象接口也是比較統(tǒng)一的,那么可以考慮在前端中對(duì)后端API接口調(diào)用進(jìn)行封裝,引入ES6的方式進(jìn)行前端API的抽象簡(jiǎn)化。2021-05-05
在Vue3項(xiàng)目中安裝和配置Three.js的操作代碼
Three.js是一個(gè)輕量級(jí)的WebGL封裝庫(kù),用于在瀏覽器中渲染復(fù)雜的3D圖形,它提供了便捷的API,可以快速構(gòu)建3D場(chǎng)景、對(duì)象和動(dòng)畫(huà),Vue.js是一個(gè)漸進(jìn)式JavaScript框架,擅長(zhǎng)構(gòu)建用戶界面,本文給大家介紹了在Vue3項(xiàng)目中安裝和配置Three.js的操作,需要的朋友可以參考下2024-12-12
vue商城中商品“篩選器”功能的實(shí)現(xiàn)代碼
這篇文章主要介紹了vue商城中商品“篩選器”功能的實(shí)現(xiàn),本文通過(guò)實(shí)例代碼給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2020-07-07
Vue3中實(shí)現(xiàn)微信掃碼登錄的步驟和代碼示例
在 Vue 3 中實(shí)現(xiàn)微信掃碼登錄,涉及到前端生成二維碼、監(jiān)聽(tīng)微信回調(diào)以及與后端的交互,本文給大家介紹了一個(gè)詳細(xì)的實(shí)現(xiàn)步驟和代碼示例,對(duì)大家的學(xué)習(xí)或工作有一定的幫助,需要的朋友可以參考下2024-07-07
解決echarts數(shù)據(jù)二次渲染不成功的問(wèn)題
這篇文章主要介紹了解決echarts數(shù)據(jù)二次渲染不成功的問(wèn)題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧2020-07-07
vue里面v-bind和Props 利用props綁定動(dòng)態(tài)數(shù)據(jù)的方法
今天小編就為大家分享一篇vue里面v-bind和Props 利用props綁定動(dòng)態(tài)數(shù)據(jù)的方法,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧2018-08-08
Vue3+Vite+TS使用elementPlus時(shí)踩的坑及解決
這篇文章主要介紹了Vue3+Vite+TS使用elementPlus時(shí)踩的坑及解決方案,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-10-10
vue3+vite+移動(dòng)端webview打包后頁(yè)面加載空白問(wèn)題解決辦法
這篇文章主要給大家介紹了關(guān)于vue3+vite+移動(dòng)端webview打包后頁(yè)面加載空白問(wèn)題的解決辦法,文中通過(guò)代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2024-06-06

