微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

使用来自 api

如何解决使用来自 api

正如我在标题中提到的,我想用 api 初始化 Chart.js 图表。我找到了教程,但它们主要是在页面呈现后更新数据。我想在呈现页面之前更新图表。所以我直接看到了初始化的图表,没有重新加载。

<template>
    <h3>Stacked</h3>
    <Chart type="bar" v-if="isReady" :data="stackedData" :options="stackedOptions"/>
</template>

<script>
import axios from "axios";
import {defineComponent,ref} from 'vue';
export default {
 
    data()  {  
 
       return {
              isReady: false,stackedData: {
                labels: ['A','B','C','D'],datasets: [{
                    type: 'bar',label: 'Something',backgroundColor: '#42A5F5',data: this.list_all
                },{
                    type: 'bar',label: 'Another',backgroundColor: '#66BB6A',data: this.list_intersection
                }]
            },stackedOptions: {
                tooltips: {
                    mode: 'index',intersect: false
                },responsive: true,scales: {
                    xAxes: [{
                        stacked: true,}],yAxes: [{
                        stacked: true
                    }]
                }
            },basicoptions: null,//---------------------------------------------------
            all:[]
            list_intersection:[],list_all:[]
        }    
    },beforeCreate() {
            let apikaderURL = 'http://localhost:4000/apikader';
            axios.get(apikaderURL).then(res => {

                this.all = res.data;
                this.saveData()
                this.isReady=true;
            }).catch(error => {
                console.log(error)
            });
        },methods:{
       saveData: function (){
          
          for (var i in this.all){
                if(this.all[i].id==='2' ){
                    this.list_all.push(this.all[i].someNumber)
                }
                if(this.all[i].id==='8'){
                    this.list_intersection.push(this.all[i].someNumber) 
                }                     
           }
           return this.list_all && this.list_intersection
       }
    }
}
</script>


我只是尝试使用 axios 获取值,对其进行过滤,然后将它们返回给图表对象的 data 属性,以便使用这些值对其进行初始化。

我想,因为我调用beforeCreate,所以它应该可以工作,因为我在渲染之前初始化了值,但图表没有显示任何值。

我也尝试过使用 vue-chartjs 来实现,但我认为它不适用于 Vue 3 或者我做错了什么。

我怎样才能做到这一点? 非常感谢您。

解决方法

生命周期钩子(如 beforeCreate 等)实际上并没有延迟后续的组件生命周期步骤,即使是异步的,它们也只是提供了一个运行代码的入口点。

使用 v-if 延迟图表的呈现,直到数据准备好。 v-if 的作用类似于 watch,在此之前根本不会呈现图表。使用 isReady 变量,您将在数据保存完成后设置该变量:

<Chart type="bar" v-if="isReady" :data="stackedData" :options="stackedOptions"/>
data()  {  
  return {
    isReady: false,...
  }
}
axios.get(apiKaderURL).then(res => {
  this.all = res.data;
  this.saveData()
  this.isReady = true;  // Triggering the `v-if`
})

(未经测试,但原则上应该可行)


此外,您不能使用 this 从另一个数据属性设置数据属性,它将是 undefined。您可以将它们设置为 null:

data: this.list_all  // Does nothing,can't use `this` like that
data: null           // Change to this

因此将其设置为 null 并修复 saveData 方法:

methods: {
  saveData() {
    const listAll = [];
    const listIntersection = [];

    for (var i in this.all){
      if(this.all[i].id==='2' ){
        listAll.push(this.all[i].someNumber)
      }
      if(this.all[i].id==='8'){
        listIntersection.push(this.all[i].someNumber) 
      }                     
    }
   
    this.stackedData.datasets[0].data = listAll;
    this.stackedData.datasets[1].data = listIntersection;
  }
}
,

我以前没有使用过 Chart.js,但我通读了安装、集成和使用文档,并提出了一个可能对您有帮助的示例(带有 Vue CLI 的 Vue 2)。

我使用我的 App.vue SFC 作为子图表组件 ChartTest.vue 的父级。在父级中,我使用“mounted”挂钩中的“setTimeout”调用模拟了 API 调用延迟。

App.vue

<template>
  <div id="app">
    <chart-test v-if="dataReady" :chartData="chartData" />
  </div>
</template>

<script>
  import ChartTest from '@/components/ChartTest'

  export default {
    name: 'App',components: {
      ChartTest
    },data() {
      return {
        chartData: [12,19,3,5,2,3],dataReady: false
      }
    },methods: {
      getData() {
        this.dataReady = true;
      }
    },mounted() {
      // Simulate API call
      setTimeout(this.getData(),2000);
    }
  }
</script>

ChartTest.vue

<template>
  <div class="chart-test">
    <h3>Chart Test</h3>
    <canvas id="my-chart" width="400" height="400" ref="chartref"></canvas>
  </div>
</template>

<script>
  import Chart from 'chart.js';

  export default {
    data() {
      return {
        myChart: null
      }
    },props: {
      chartData: {
        type: Array,required: true
      }
    },mounted() {
      this.myChart = new Chart(this.$refs.chartref,{
        type: 'bar',data: {
          labels: ['Red','Blue','Yellow','Green','Purple','Orange'],datasets: [{
            label: '# of Votes',data: this.chartData,backgroundColor: [
              'rgba(255,99,132,0.2)','rgba(54,162,235,'rgba(255,206,86,'rgba(75,192,'rgba(153,102,255,159,64,0.2)'
            ],borderColor: [
              'rgba(255,1)',1)'
            ],borderWidth: 1
          }]
        },options: {
          scales: {
            yAxes: [{
              ticks: {
                beginAtZero: true
              }
            }]
          }
        }
      });
    }
  }
</script>

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其他元素将获得点击?
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。)
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbcDriver发生异常。为什么?
这是用Java进行XML解析的最佳库。
Java的PriorityQueue的内置迭代器不会以任何特定顺序遍历数据结构。为什么?
如何在Java中聆听按键时移动图像。
Java“Program to an interface”。这是什么意思?