You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在<script setup>中更新vue-chartjs图表?点击按钮不生效问题

解决vue-chartjs点击按钮后图表不更新的问题

问题分析

你遇到的核心问题是:虽然修改了chartData的内部属性,但vue-chartjs组件没有检测到数据变化从而重新渲染。这是因为Vue的响应式系统虽然能追踪对象内部属性的变化,但部分第三方组件(包括vue-chartjs)可能需要整个数据对象的引用变化才能触发更新,或者需要显式调用图表的更新方法。另外你的chartOptions设置为ref(true)是错误的,应该传入图表配置对象。

解决方案

方案1:替换整个chartData对象(最简单)

直接给chartData.value赋值一个全新的对象,让Vue的响应式系统检测到引用变化,从而触发组件重新渲染:

<template>
  {{ chartData }}
  <Bar
    id="my-chart-id"
    :options="chartOptions"
    :data="chartData"
  />
  <button
    @click="update()"
    class="bg-blue-500 hover:bg-blue-700 text-white font-bold py-2 px-4 rounded"
  >
    Button
  </button>
</template>

<script setup>
import { Bar } from "vue-chartjs";
import { ref } from "vue";
import {
  Chart as ChartJS,
  Title,
  Tooltip,
  Legend,
  BarElement,
  CategoryScale,
  LinearScale,
} from "chart.js";

ChartJS.register(
  Title,
  Tooltip,
  Legend,
  BarElement,
  CategoryScale,
  LinearScale
);

const chartData = ref({
  labels: ["January", "February", "March"],
  datasets: [{ data: [40, 20, 12] }],
});
// 修正chartOptions为正确的配置对象
const chartOptions = ref({
  responsive: true,
  maintainAspectRatio: false
});

function update() {
  // 替换整个chartData对象,保留原有labels等属性
  chartData.value = {
    ...chartData.value,
    datasets: [{ data: [0, 2, 2] }]
  };
}
</script>

方案2:使用computed包装数据(符合文档推荐)

在<script setup>中使用computed非常简单,只需导入后定义计算属性,依赖变化时计算属性会返回新的引用,触发图表更新:

<template>
  {{ computedChartData }}
  <Bar
    id="my-chart-id"
    :options="chartOptions"
    :data="computedChartData"
  />
  <button
    @click="update()"
    class="bg-blue-500 hover:bg-blue-700 text-white font-bold py-2 px-4 rounded"
  >
    Button
  </button>
</template>

<script setup>
import { Bar } from "vue-chartjs";
import { ref, computed } from "vue";
import {
  Chart as ChartJS,
  Title,
  Tooltip,
  Legend,
  BarElement,
  CategoryScale,
  LinearScale,
} from "chart.js";

ChartJS.register(
  Title,
  Tooltip,
  Legend,
  BarElement,
  CategoryScale,
  LinearScale
);

const rawChartData = ref({
  labels: ["January", "February", "March"],
  datasets: [{ data: [40, 20, 12] }],
});
const chartOptions = ref({
  responsive: true
});

// 使用computed包装数据,依赖变化时自动返回新对象
const computedChartData = computed(() => ({
  ...rawChartData.value
}));

function update() {
  // 修改原始数据,computed会自动追踪变化
  rawChartData.value.datasets = [{ data: [0, 2, 2] }];
}
</script>

方案3:获取图表实例显式调用update(性能最优)

如果只需要修改部分数据,不想重新渲染整个组件,可以通过ref获取图表实例,直接调用其update()方法:

<template>
  {{ chartData }}
  <Bar
    ref="chartRef"
    id="my-chart-id"
    :options="chartOptions"
    :data="chartData"
  />
  <button
    @click="update()"
    class="bg-blue-500 hover:bg-blue-700 text-white font-bold py-2 px-4 rounded"
  >
    Button
  </button>
</template>

<script setup>
import { Bar } from "vue-chartjs";
import { ref } from "vue";
import {
  Chart as ChartJS,
  Title,
  Tooltip,
  Legend,
  BarElement,
  CategoryScale,
  LinearScale,
} from "chart.js";

ChartJS.register(
  Title,
  Tooltip,
  Legend,
  BarElement,
  CategoryScale,
  LinearScale
);

const chartRef = ref(null);
const chartData = ref({
  labels: ["January", "February", "March"],
  datasets: [{ data: [40, 20, 12] }],
});
const chartOptions = ref({
  responsive: true
});

function update() {
  // 直接修改数据
  chartData.value.datasets[0].data = [0, 2, 2];
  // 获取图表实例并触发更新
  if (chartRef.value) {
    chartRef.value.update();
  }
}
</script>

关于

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.26 18:07:06