123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105 |
- <template>
- <div ref="canvas" class="canvas" />
- </template>
- <script setup lang="ts" name="Chart">
- import ElementResizeDetectorMaker from 'element-resize-detector';
- import { autoToolTip } from './echarts_auto_tooltip';
- import * as echarts from 'echarts';
- import { onUnmounted } from 'vue';
- interface Props {
- option: object;
- rotation?: boolean;
- chartClick?: Function;
- legendChange?: Function;
- }
- const props = withDefaults(defineProps<Props>(), {
- rotation: false,
- legendChange: () => {}
- });
- const emits = defineEmits(['ready', 'click']);
- // 渲染容器
- const canvas = ref<HTMLElement>();
- // echarts
- const myChart = shallowRef(null);
- // 加载状态
- let loaded = ref(false);
- watch(
- props.option,
- () => {
- if (Object.keys(props.option).length !== 0) {
- if (loaded.value && !!myChart.value) {
- myChart.value.setOption(props.option, true);
- } else {
- load();
- }
- } else if (!!myChart.value) {
- myChart.value.clear();
- }
- },
- {
- deep: true
- }
- );
- // 加载事件
- const load = () => {
- if (!myChart.value || Object.keys(myChart.value).length === 0) {
- myChart.value = echarts.init(canvas.value);
- }
- // 基于准备好的dom,初始化echarts实例
- myChart.value.clear();
- myChart.value.setOption(props.option);
- // 监听元素变化
- const erd = ElementResizeDetectorMaker();
- erd.listenTo(canvas.value, function () {
- nextTick(function () {
- // 使echarts尺寸重置
- setTimeout(function () {
- myChart.value.resize();
- }, 500);
- });
- });
- if (props.rotation) {
- autoToolTip(myChart.value, props.option, { loopSeries: true });
- }
- emits('ready', myChart.value);
- // 监听点击事件
- if (props.chartClick) {
- myChart.value.off('click', handleClick);
- myChart.value.on('click', handleClick);
- }
- if (props.legendChange) {
- myChart.value.on('legendselectchanged', function (params) {
- props.legendChange(params, myChart.value);
- });
- }
- loaded.value = true;
- };
- const handleClick = (params: any) => {
- props.chartClick(params);
- };
- onMounted(() => {
- if (!(JSON.stringify(props.option) === '{}')) {
- load();
- }
- });
- onUnmounted(() => {
- myChart.value = null;
- });
- </script>
- <style lang="scss" scoped>
- .canvas {
- width: 100%;
- height: 100%;
- // flex: 1;
- }
- </style>
|