Vue js + HighChart-如何在呈现组件之前进行同步axios调用?

问题描述 投票:0回答:1

[亲爱的,我是vue js的新手。我做了一个vue js + NUXT小程序,用HighCharts渲染了一个图表。通过网络服务调用axios检索数据。

问题:Web服务调用变得异步并且我的图表已经初始化。如何在呈现图表之前使呼叫同步?

虽然Highchart本身需要时间来初始化,但我不得不使用它来设置超时功能。如果您忽略了这个问题,那么我会遇到这样的问题:图表初始化时会设置数据,这会导致图表显示错误的问题。

<template>
  <div>
  <highcharts :options="chartOptions"></highcharts>
  </div>
</template>
<script>
    import axios from 'axios';
    import {Chart} from 'highcharts-vue'
    import Highcharts3D from 'highcharts/highcharts-3d'
    import Highcharts from 'highcharts'

    if (typeof Highcharts === 'object') {
        Highcharts3D(Highcharts);
    }

    export default {
        layout: 'contentOnly',
        auth: false,
        components: {
            highcharts: Chart
        },
        data() {
            return {
                data: [],
                chartOptions: {
                    title: {
                        text: ''
                    },
                    tooltip: {
                        pointFormat: '{point.percentage:.2f}%',
                    },
                    chart: {
                        type: 'pie',
                        options3d: {
                            enabled: true,
                            alpha: 50,
                        },
                        // plotBackgroundColor: 0,
                        // plotBorderWidth: 0,
                        // plotShadow: true,
                    },
                    series: [{
                        name: '',
                        data: [1],
                        tooltip: {
                            valueDecimals: 0
                        }
                    }],
                    plotOptions: {
                        pie: {
                            allowPointSelect: true,
                            cursor: 'pointer',
                            innerSize: '30%',
                            depth: 100,
                            dataLabels: {
                                enabled: true,
                                percentageDecimals: 2,
                                color: '#002a52',
                                connectorColor: '#002a52',
                                formatter: function () {
                                    return '<b>' + this.point.name + '</b>: ' + this.percentage.toFixed(2) + ' %';
                                }
                            }
                        }
                    },

                    credits: {
                        enabled: false
                    },
                    exporting: {
                        buttons: {
                            printButton: {
                                enabled: false
                            },
                            contextButton: {
                                enabled: false
                            }
                        }
                    },
                }
            };
        },
        mounted() {
            this.fetchData()
            setTimeout(function(){ 
                let data = []
                var index = 0
                for (var key in this.data) {
                    data[index] = []
                    data[index][0] = key
                    if (key == '30') data[index][0] = '< 30'
                    if (key == '999') data[index][0] = '> 65'
                    data[index][1] = this.data[key]
                    index++;
                }
                this.chartOptions.series[0].data = data
           }.bind(this), 1000);
        },
        methods: {
            fetchData() {       
                axios.post(this.$axios.defaults.baseURL + 'api/analytics/age', {
                    locale: this.$i18n.locale,
                    onlyPaid: this.$route.query.onlyPaid
                }).then(response => {
                    this.data = response.data
                }).catch(e => {
                    console.log(e)
                })
            }
        }
    }
</script>
vue.js highcharts axios nuxt
1个回答
0
投票

[您不认为您需要使呼叫同步,只需等待网络服务完成然后显示图表,我通常使用布尔值说'isChartDataLoaded'(这是我更新代码所用的语言。) >

  import axios from 'axios';
  import {Chart} from 'highcharts-vue'
  import Highcharts3D from 'highcharts/highcharts-3d'
  import Highcharts from 'highcharts'

  if (typeof Highcharts === 'object') {
      Highcharts3D(Highcharts);
  }

  export default {
      layout: 'contentOnly',
      auth: false,
      components: {
          highcharts: Chart
      },
      data() {
          return {
              isChartDataLoaded : false,
              data: [],
              chartOptions: {
                  title: {
                      text: ''
                  },
                  tooltip: {
                      pointFormat: '{point.percentage:.2f}%',
                  },
                  chart: {
                      type: 'pie',
                      options3d: {
                          enabled: true,
                          alpha: 50,
                      },
                      // plotBackgroundColor: 0,
                      // plotBorderWidth: 0,
                      // plotShadow: true,
                  },
                  series: [{
                      name: '',
                      data: [1],
                      tooltip: {
                          valueDecimals: 0
                      }
                  }],
                  plotOptions: {
                      pie: {
                          allowPointSelect: true,
                          cursor: 'pointer',
                          innerSize: '30%',
                          depth: 100,
                          dataLabels: {
                              enabled: true,
                              percentageDecimals: 2,
                              color: '#002a52',
                              connectorColor: '#002a52',
                              formatter: function () {
                                  return '<b>' + this.point.name + '</b>: ' + this.percentage.toFixed(2) + ' %';
                              }
                          }
                      }
                  },

                  credits: {
                      enabled: false
                  },
                  exporting: {
                      buttons: {
                          printButton: {
                              enabled: false
                          },
                          contextButton: {
                              enabled: false
                          }
                      }
                  },
              }
          };
      },
      mounted() {
          this.fetchData()
          setTimeout(function(){ 
              let data = []
              var index = 0
              for (var key in this.data) {
                  data[index] = []
                  data[index][0] = key
                  if (key == '30') data[index][0] = '< 30'
                  if (key == '999') data[index][0] = '> 65'
                  data[index][1] = this.data[key]
                  index++;
              }
              this.chartOptions.series[0].data = data
         }.bind(this), 1000);
      },
      methods: {
          fetchData() {       
              this.isChartDataLoaded = false;
              axios.post(this.$axios.defaults.baseURL + 'api/analytics/age', {
                  locale: this.$i18n.locale,
                  onlyPaid: this.$route.query.onlyPaid
              }).then(response => {
                  this.data = response.data;
                  this.isChartDataLoaded = true;
              }).catch(e => {
                  console.log(e)
              })
          }
      }
  }
<template>
  <div v-if="isChartDataLoaded">
    <highcharts :options="chartOptions"></highcharts>
  </div>
</template>
© www.soinside.com 2019 - 2024. All rights reserved.