Map/Stock not loading when packaged through webpack
thedamon opened this issue · 8 comments
I'm trying to initialize a highmap inside a ".vue" component being packaged by Webpack. I'm following the procedure to use Vue.use(VueHighcharts, { Highcharts });
with a Highcharts loaded from highmaps but in my template <highmaps>
is not being registered as a vue component.. <highcharts>
and <highcharts-renderer>
are, though.
My component looks like this:
https://gist.github.com/thedamon/ed9dc91e65dfb014bc99206e46b0738d
As you import Highcharts from 'highcharts/highmaps'
, which is already include highmaps, you don't need load map from 'highcharts/modules/map'
again.
import Vue from 'vue';
import VueHighcharts from 'vue-highcharts';
import Highcharts from 'highcharts/highmaps';
Vue.use(VueHighcharts, { Highcharts });
Live example: https://codesandbox.io/s/o48pkv67r9
Thanks for the example. I have exactly that code now except for the name of my main app.. but for me the component isn't working. I was using it as a component within another component, but re did it to look like the codesandbox
. Really perplexed about what the difference might be
Maybe you can try to import highcharts and vue-highcharts in your entry file and Vue.use it.
It appears that highmaps won't work if it's being imported dynamically. My import was in this listener
document.addEventListener('DOMContentLoaded', function(event) {
if (document.getElementById('fundData')) {
import(/* webpackChunkName: "chartComponents" */ './chartComponentsIndex');
}
});
And it failed silently. Can you think of why this would be and if there is a way around it? I want to confine the heavy highcharts related code to being loaded only when it's used.
Once I did as you suggested it started initializing highmaps, but my piechart and barchart components started throwing an error The requested series type does not exist
.
I'm not clear about what is in ./fundDataIndex
and which part of your code is imported dynamically. But if you want to load highmaps async, you should also load vue-highcharts async and then Vue.use it.
Example: https://codesandbox.io/s/xp7m85ypmo
The way I'm doing it is a little different with a dynamic import and then loading the data for the components via a service. I put the structure up on codesandbox, though it won't function without the endpoint and I'm not sure if codesandbox supports the dynamic webpack imports (it requires a babel plugin to support the import() syntax)
https://codesandbox.io/s/lx1yqq9nz9
If you see something that makes sense in keeping those from working.. the other types of charts are functioning exactly as expected. The loading process is a bit complex so I'm not sure how to mirror it online easily, but I'll try and work up a complete example maybe using require.ensure
if nothing sticks out
OK, let me try to explain:
In chartRenderer.vue
, you import pieChart.vue
and then mapChart.vue
, so we jump into pieChart.vue
, you call Vue.use(VueHighcharts)
without passing in a Highcharts
object, vue-highcharts will import Highcharts from 'highcharts'
by default, which point to highcharts/highcharts.js
file. Then in mapChart.vue
, you try to import Highcharts from 'highcharts/highmaps.js'
, a different file, means the two Highcharts
object don't have same reference. But it's not the point, you then call Vue.use(VueHighcharts, { Highcharts })
again, Vue will automatically prevents you from using the same plugin more than once, so the Highcharts
object inside vue-highcharts is still highcharts/highcharts.js
.
To fix this problem, the key point is make sure all Highcharts
have same reference. So always import Highcharts from 'highcharts'
and use add-ons by loading corresponding modules.
// pieChart.vue
import Vue from 'vue';
import VueHighcharts from 'vue-highcharts';
import Highcharts from 'highcharts';
Vue.use(VueHighcharts, { Highcharts });
// mapChart.vue
import Vue from 'vue';
import VueHighcharts from 'vue-highcharts';
import Highcharts from 'highcharts';
import loadMap from 'highcharts/modules/map';
loadMap(Highcharts);
// maybe we don't want to figure out which fooChart.vue is loaded first,
// just write it and Vue will handle it.
Vue.use(VueHighcharts, { Highcharts });
I'm closing this issue for it is not about vue-highcharts itself, and my comment above should figure out the reason.