chartManager.ts 1.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778
  1. import { onMounted, onUnmounted, ref } from 'vue'
  2. import * as echarts from 'echarts'
  3. const chartInstances: Map<string, echarts.ECharts> = new Map()
  4. let instanceCounter = 0
  5. export const windowSize = ref({
  6. width: window.innerWidth,
  7. height: window.innerHeight,
  8. })
  9. export function addChartInstance(chart: echarts.ECharts) {
  10. const id = `chart_${instanceCounter++}`
  11. chartInstances.set(id, chart)
  12. return id
  13. }
  14. export function removeChartInstance(id: string) {
  15. const chart = chartInstances.get(id)
  16. if (chart) {
  17. chartInstances.delete(id)
  18. try {
  19. chart.dispose()
  20. } catch (error) {
  21. console.warn('Chart dispose failed:', error)
  22. }
  23. }
  24. }
  25. export function safeInitChart(dom: HTMLElement): echarts.ECharts {
  26. const existing = echarts.getInstanceByDom(dom)
  27. if (existing) {
  28. echarts.dispose(dom)
  29. }
  30. return echarts.init(dom)
  31. }
  32. export function useResponsiveLayout() {
  33. const handleResize = () => {
  34. windowSize.value = {
  35. width: window.innerWidth,
  36. height: window.innerHeight,
  37. }
  38. requestAnimationFrame(() => {
  39. chartInstances.forEach((chart, id) => {
  40. try {
  41. if (chart.getDom()) {
  42. chart.resize()
  43. } else {
  44. console.warn(`Chart ${id} 已被销毁或 DOM 不存在,跳过 resize`)
  45. }
  46. } catch (error) {
  47. console.warn(`Chart resize failed for ${id}:`, error)
  48. }
  49. })
  50. })
  51. }
  52. onMounted(() => {
  53. window.addEventListener('resize', handleResize)
  54. handleResize()
  55. })
  56. onUnmounted(() => {
  57. window.removeEventListener('resize', handleResize)
  58. chartInstances.forEach((chart) => {
  59. try {
  60. chart.dispose()
  61. } catch (error) {
  62. console.warn('Chart dispose failed during cleanup:', error)
  63. }
  64. })
  65. chartInstances.clear()
  66. })
  67. return { windowSize }
  68. }