I would like to add an interactive map to my Nuxt.js website. I simply created a component that consists of the world map with AmCharts lib. My goal is to change the color of some countries (France in my example) if a button is clicked. Here is what my file looks like:
// components/Map.vue
<template>
<div>
<div id="chartdiv"/>
<button @click="colorMe()">Click me!</button>
</div>
</template>
<script>
import * as am4core from "@amcharts/amcharts4/core";
import * as am4maps from "@amcharts/amcharts4/maps";
import am4geodata_worldUltra from "@amcharts/amcharts4-geodata/worldUltra";
export default {
methods: {
colorMe() {
worldPolygonSeries.getPolygonById("FR").fill = am4core.color("#f00");
}
},
mounted() {
// Create map instance
let map = am4core.create("chartdiv", am4maps.MapChart);
// Set map definition
map.geodata = am4geodata_worldUltra;
// Set projection
map.projection = new am4maps.projections.Miller();
// Zoom control
map.zoomControl = new am4maps.ZoomControl();
// The world
let worldPolygonSeries = map.series.push(new am4maps.MapPolygonSeries());
worldPolygonSeries.useGeodata = true;
}
}
</script>
<style scoped>
#chartdiv {
width: 100%;
height: 350px;
}
</style>
The error I get when I click the button is worldPolygonSeries is not defined
. So I tried to create map
and worldPolygonSeries
directly inside the data part and to pass it as parameters but this isn't working...
Something like this:
export default {
data() {
return {
map: am4core.create("chartdiv", am4maps.MapChart),
worldPolygonSeries: map.series.push(new am4maps.MapPolygonSeries())
}
},
methods: {
colorMe(worldPolygonSeries) {
worldPolygonSeries.getPolygonById("FR").fill = am4core.color("#f00");
}
},
mounted(map, worldPolygonSeries) {
// Set map definition
map.geodata = am4geodata_worldUltra;
// Set projection
map.projection = new am4maps.projections.Miller();
// Zoom control
map.zoomControl = new am4maps.ZoomControl();
// The world
worldPolygonSeries.useGeodata = true;
}
}
So now the error I get is Cannot set property 'geodata' of undefined
. Is someone has any idea of how I can manage my code to reach my goal?
Ok I got it!
I just change my variables to undefined on the data part, then I could access it from mounted
and methods
.
// components/Map.vue
<template>
<div>
<div id="chartdiv" class="h-96"/>
<button @click="colorMe(worldPolygonSeries)">Click me!</button>
</div>
</template>
<script>
import * as am4core from "@amcharts/amcharts4/core";
import * as am4maps from "@amcharts/amcharts4/maps";
import am4geodata_worldUltra from "@amcharts/amcharts4-geodata/worldUltra";
export default {
data() {
return {
map: undefined,
worldPolygonSeries: undefined
}
},
methods: {
colorMe(worldPolygonSeries) {
worldPolygonSeries.getPolygonById("FR").fill = am4core.color("#f00");
}
},
mounted() {
// Create map instance
this.map = am4core.create("chartdiv", am4maps.MapChart);
// Set map definition
this.map.geodata = am4geodata_worldUltra;
// Set projection
this.map.projection = new am4maps.projections.Miller();
// Zoom control
this.map.zoomControl = new am4maps.ZoomControl();
// The world
this.worldPolygonSeries = this.map.series.push(new am4maps.MapPolygonSeries());
this.worldPolygonSeries.useGeodata = true;
}
}
</script>
<style scoped>
#chartdiv {
width: 100%;
height: 350px;
}
</style>
Thanks for your help Iman ;)