ECharts のグラフは要素幅が動的に変更された場合にそれに合わせてリサイズしてくれないため、リサイズしたい場合は都度 resize
メソッドを実行する必要がある。
ピュアな (?) JavaScript アプリであれば window
オブジェクトの 'resize'
イベントを監視して chart.resize()
するだけで十分だが、Vue のような VirtualDOM ライブラリを利用している場合は「ウィンドウサイズ」というグローバルな状態をどう扱うかをちゃんと考えないといけない。
昔は Vuex を使って「ウィンドウサイズをちゃんとした状態として扱う」ことでこれ実現するなどしていたが、Vue 2.6.0 で追加された Vue.observable
を使えば Vuex を使わずとも簡単に書けることを知ったので方法をまとめておく。
ウィンドウサイズを監視できるようにする
Vue インスタンスプロパティ $window
を追加して、Vue コンポーネントからウィンドウサイズを監視できるようにする。
参考: [Nuxt.js, Vue.js] Vue コンポーネントで Window のリサイズ/スクロールを監視するとてもよい方法 - やくだつブログ
import Vue from 'vue'
const WindowSizePlugin = {
install(Vue) {
const $window = Vue.observable({ width: 0, height: 0 })
if (process.client) {
function onResize() {
$window.width = document.documentElement.clientWidth
$window.height = document.documentElement.clientHeight
}
window.addEventListener('resize', onResize)
onResize()
}
Vue.prototype.$window = $window
}
}
Vue.use(WindowSizePlugin)
Nuxt.js の場合は上記を plugins/window.js
に配置して、 nuxt.config.js
の plugin
に '@/plugins/window'
を追加する。
ECharts を利用するコンポーネントからウィンドウサイズを監視する
watch
プロパティで $window.width
を監視して、変更されたらグラフをリサイズする処理を実行する。
<template>
<div></div>
</template>
<script>
import { init } from 'echarts'
export default {
props: {
option: {
type: Object,
},
},
data() {
return {
chart: null,
}
},
mounted() {
this.chart = init(this.$el)
this.chart.setOption(this.option)
},
watch: {
option() {
this.chart.setOption(this.option)
},
'$window.width'() {
this.chart.resize()
},
},
}
</script>