效果图
前提
引入echarts,百度地图
index.html文件中 引入
<script src="static/js/5.3.0-echarts.min.js"></script>
<script src="https://api.map.baidu.com/api?v=3.0&ak=***"></script>
注意:ak 为百度地图的秘钥,必须是v=3.0,5.3.0-echarts.min.js文件在Json/js中,将此文件放在static/js中,在index.html中引入
项目结构
html部分
<template>
<div class="container">
<div v-show="areaLeval < 3" id="chinaMap"></div>
<div v-show="areaLeval == 3" id="countyMap"></div>
<div class="back" @click="back">返回</div>
</div>
</template>
html分为三部分,echarts id为chinaMap、百度地图 id为countyMap,以及返回按钮
script部分
地图展示
初始化显示全国地图;
点击全国中的省显示当前省全部的市;
点击省下的市显示当前市下的全部区县;
点击全部区县下的某个区县显示单独某个区县;
标注点
标注点区分状态:
没有状态的时候显示静态红点
有状态的时候水波纹显示
(提示:可根据不同的状态更换不同颜色的图标)
弹框信息
可以点击标注点,通过接口获取弹框信息,显示弹框内容
地图显示不同颜色
可根据条件,让地图模块儿显示不同的颜色
<script>
import chinaJson from './Json/china.json'
import {cityProMap} from './Json/cityProMap.js'
import MapMaker from "./Json/js/MapMaker.js"
import { color } from './Json/js/colorSet.js'
export default {
data(){
return{
map:null,
chart: null, // 实例化echarts
zoom:1.2,//地图缩放级别
special: ["北京", "天津", "上海", "重庆", "香港", "澳门","台湾"],
areaLeval:0, //0 默认全国
address:[],
addressCode:[],
regions:[],//行政区域颜色数据
pointData:[],//标注点
icon:require('@/views/demo/Json/imgs/circle.png')
}
},
mounted(){
this.init()
},
methods:{
//--------------------------------------接口获取数据--------------------------------
//接口获取标注点
getPointArr(id) {
let res1 = {
'code':0,
'data':{
'list':[
{
'id':'130000',
'name':'河北省',
'center':[115.502461,38.445474],
'value':50,
'alarmState':true
},
],
},
'msg':'操作成功'
}
let res2 = {
'code':0,
'data':{
'list':[
{
'id':'130100',
'name':'石家庄市',
'center':[114.502461, 38.045474],
'value':20,
'alarmState':true
},
],
},
'msg':'操作成功'
}
let res3 = {
'code':0,
'data':{
'list':[
{
'id':'130123',
'name':'正定县',
'center':[114.569887,38.147835],
'value':40,
'alarmState':true
},
],
},
'msg':'操作成功'
}
let res4 = {
'code':0,
'data':{
'list':[
{
'id':'2335585222',
'name':'荣国府',
'center':[114.585662,38.154535],
'value':80,
'alarmState':true
},
],
},
'msg':'操作成功'
}
if(this.areaLeval == 0) {
this.pointData = res1.data.list
} else if (this.areaLeval == 1) {
this.pointData = res2.data.list
} else if (this.areaLeval == 2) {
this.pointData = res3.data.list
} else if (this.areaLeval == 3) {
this.pointData = res4.data.list
}
},
//接口获取标注点弹框信息
getInfo(id,callback){
let res1 = {
'code':0,
'data':{
'name':'河北省',
'content':'这是河北省'
},
'msg':'操作成功'
}
let res2 = {
'code':0,
'data':{
'name':'石家庄市',
'content':'这是石家庄市'
},
'msg':'操作成功'
}
let res3 = {
'code':0,
'data':{
'name':'正定县',
'content':'这是正定县'
},
'msg':'操作成功'
}
let res4 = {
'code':0,
'data':{
'name':'荣国府',
'content':'这是荣国府'
},
'msg':'操作成功'
}
if (callback) {
if(this.areaLeval == 0) {
callback(res1)
} else if(this.areaLeval == 1) {
callback(res2)
} else if(this.areaLeval == 2) {
callback(res3)
} else if(this.areaLeval == 3) {
callback(res4)
}
}
},
//---------------------------------------以下echart-----------------------------------
//初始化数据
init(){
this.getPointArr('1')
this.$nextTick(() => {
this.chart = echarts.init(document.getElementById('chinaMap'));
this.requestGetChinaJson();
this.chart.on("click", this.echartsMapClick);
});
},
//加载全国地图
requestGetChinaJson(){
this.getPointArr('1')
this.zoom = 1.2
this.chinaData = chinaJson.data
//region数据处理
let arr = []
this.chinaData.features.forEach(item=>{
let obj = {}
obj.id = item.id
obj.name = item.properties.name
obj.center = item.properties.cp
obj.itemStyle ={
normal: {areaColor: ""},
emphasis: {areaColor: ""},
}
arr.push(obj)
})
this.setAreaColor(arr)
this.regions = arr
//注册地图
echarts.registerMap("china", chinaJson.data);
//渲染地图
this.renderMap("china")
},
//加载省级地图
requestGetProvinceJSON(id) {
this.getPointArr(id)
this.provinceData = require(`./Json/province/${id}.json`)
//region数据处理
let arr = []
this.provinceData.features.forEach(item=>{
let obj = {}
obj.id = item.properties.adcode
obj.name = item.properties.name
obj.center = item.properties.center
obj.itemStyle ={
normal: {areaColor: ""},
emphasis: {areaColor: ""},
}
arr.push(obj)
})
this.setAreaColor(arr)
this.regions = arr
//注册地图
echarts.registerMap("province", this.provinceData);
//渲染地图
this.renderMap("province")
},
//加载市级地图
requestGetCityJSON(id) {
this.getPointArr(id)
this.cityData = require(`./Json/city/${id}.json`)
//region数据处理
let arr = []
this.cityData.features.forEach(item=>{
let obj = {}
obj.id = item.properties.adcode
obj.name = item.properties.name
obj.center = item.properties.center
obj.itemStyle = {
normal: {areaColor: ""},
emphasis: {areaColor: ""},
}
arr.push(obj)
})
this.setAreaColor(arr)
this.regions = arr
//注册地图
echarts.registerMap("city", this.cityData);
//渲染地图
this.renderMap("city")
},
//设置地区颜色
setAreaColor(arr) {
if(this.pointData.length) { //获取的标注点的数据
this.pointData.forEach(item1=>{
arr.forEach(item2=>{
if(item1.id == item2.id) {
if(item1.value == 0) {
item2.itemStyle.normal.areaColor = color[item1.value]
item2.itemStyle.emphasis.areaColor = color[item1.value]
} else {
item2.itemStyle.normal.areaColor = color[item1.value-1]
item2.itemStyle.emphasis.areaColor = color[item1.value-1]
}
}else {
item2.itemStyle.normal.areaColor = '#ffffff'
item2.itemStyle.emphasis.areaColor = '#ffffff'
}
})
})
}
},
//渲染地图
renderMap(map){
let _that = this
let option = {
tooltip:{
show:false,
formatter:"",
},
geo: {
map: map,
type: "map",
zoom: _that.zoom,
label: {
show: true,
color: "#333",
fontSize:10,
},
emphasis: {
label:{
show: true,
color: "#333",
fontSize:10,
}
},
roam: false,
itemStyle: {
fontSize:12,
areaColor: "#DAE7F1",
borderColor: "#0692a4",
},
regions:_that.regions,
},
series:_that.pointData.length?_that.setSerices(_that.pointData,map):[]
}
//防止重复触发点击事件
this.chart.off('mouseover') // 这里很重要!!!
this.chart.on('mouseover', function(param) {
// 这个param可以获取你要的图中的当前点击的项的参数
if(param.componentType == "series") {
_that.getInfo(param.data.id,(res)=>{
option.series.forEach((tool,index)=>{
option.series[index].tooltip.formatter = `
名称:${res.data.name}<br>
内容:${res.data.content}`
option.series[index].tooltip.show = true
})
_that.chart.setOption(option);
}
)
}
});
this.chart.off('mouseout') // 这里很重要!!!
this.chart.on('mouseout', function(param) {
//这个param可以获取你要的图中的当前点击的项的参数
option.series.forEach((tool,index)=>{
option.series[index].tooltip.formatter = ""
option.series[index].tooltip.show = false
})
_that.chart.setOption(option);
});
//渲染地图
this.chart.setOption(option);
},
//设置数据
setSerices(item,map) {
let _that = this
let item1 = [],item2 = []
if(item.length){
item.forEach((sta)=>{
if(sta.alarmState) {
item2.push(sta)
}else {
item1.push(sta)
}
})
}
let service = [
{
map: map,
type: "scatter",
coordinateSystem: "geo",
zlevel: 2,
rippleEffect: {
color:'red',
period:2,
scale:2.5,
brushType: "fill",
},
label: {
show:false,
},
emphasis: {
label: {
show: false
}
},
symbol:"image://"+_that.icon,
symbolSize:15,
tooltip: {
show:false,
// 浮窗位置
position: function (point, params, dom, rect, size) {
var x = 0;
var y = 0;
var pointX = point[0];
var pointY = point[1];
var boxWidth = size.contentSize[0];
var boxHeight = size.contentSize[1];
if (boxWidth > pointX) {
x = 5;
} else { // 左边放的下
x = pointX - boxWidth;
}
if (boxHeight > pointY) {
y = 5;
} else { // 上边放得下
y = pointY - boxHeight;
}
return [x, y];
},
formatter:"",
},
data: item1.length?item1.map(function (dataItem) {
return {
id:dataItem.id,
name: dataItem.name,
value: dataItem.center?dataItem.center.concat([dataItem.value]):0,
};
}):[],
},
{
map: map,
type: "effectScatter",
coordinateSystem: "geo",
zlevel: 2,
rippleEffect: {
color:'red',
period:2,
scale:3,
brushType: "fill",
},
label: {
show:false,
},
emphasis: {
label: {
show: false
}
},
symbol:"image://"+_that.icon,
symbolSize:9,
tooltip: {
show:false,
// 浮窗位置
position: function (point, params, dom, rect, size) {
var x = 0;
var y = 0;
var pointX = point[0];
var pointY = point[1];
var boxWidth = size.contentSize[0];
var boxHeight = size.contentSize[1];
if (boxWidth > pointX) {
x = 5;
} else { // 左边放的下
x = pointX - boxWidth;
}
if (boxHeight > pointY) {
y = 5;
} else { // 上边放得下
y = pointY - boxHeight;
}
return [x, y];
},
formatter:"",
},
data: item2.length?item2.map(function (dataItem) {
return {
id:dataItem.id,
name: dataItem.name,
value: dataItem.center?dataItem.center.concat([dataItem.value]):0,
};
}):[],
},
]
return service
},
//点击地图
echartsMapClick(params) {
if(params.name == '南海诸岛') {
alert('当前地区为南海诸岛')
return
}
if (params.region.id in cityProMap.provincesCode) {
//如果点击的是34个省、市、自治区,绘制选中地区的二级地图
this.areaLeval = 1
this.address[0] = params.region.name
this.addressCode[0] = params.region.id
this.requestGetProvinceJSON(params.region.id)
} else if (params.region.id in cityProMap.areaMap1) {
//显示市级地图
this.areaLeval = 2
this.address[1] = params.region.name
this.addressCode[1] = params.region.id
this.requestGetCityJSON(params.region.id)
} else {
//显示区县地图
this.areaLeval = 3
if(!this.address[1]) {
this.address[1] = ''
}
this.address[2] = params.region.name
this.addressCode[2] = params.region.id
this.getPointArr(params.region.id)
this.$nextTick(()=>{
this.initMap(this.address,params.region.center,params)
})
}
},
//-----------------------------------以下百度地图------------------------
//加载区县地图
initMap(name,center,params){
// 传入密钥获取地图回调。
// 创建地图实例
let map = new BMap.Map("countyMap");
// 创建点坐标 axios => res 获取的初始化定位坐标
let point = new BMap.Point(center[0],center[1])
// 初始化地图,设置中心点坐标和地图级别
map.centerAndZoom(point, 12)
//开启鼠标滚轮缩放
map.enableScrollWheelZoom(false)
//绘制中国区域行政边界---区/县地图
this.getBoundary(map,name,center,params)
},
//绘制中国区域行政边界---区/县地图
getBoundary(map,name,center,params){
let _this = this
var bdary = new BMap.Boundary();
bdary.get(name.join(''), function(rs){ //获取行政区域
map.clearOverlays(); //清除地图覆盖物
var count = rs.boundaries.length; //行政区域的点有多少个
if (count === 0) {
alert('未能获取当前输入行政区域');
return ;
}
var EN_JW = "180, 90;";//东北角
var NW_JW = "-180, 90;";//西北角
var WS_JW = "-180, -90;";//西南角
var SE_JW = "180, -90;";//东南角
//添加环形遮罩层
for (var i = 0; i < count; i++) {
var ply1 = new BMap.Polygon(rs.boundaries[i] + SE_JW + SE_JW + WS_JW + NW_JW + EN_JW + SE_JW, {
strokeOpacity: 1, strokeColor: "#123258",
strokeWeight: 1, fillColor: "#123258",fillOpacity: 1
}); //建立多边形覆盖物
}
map.addOverlay(ply1);
var pointDataay = [];
for (var i = 0; i < count; i++) {
var ply = new BMap.Polygon(rs.boundaries[i],{
strokeOpacity: 1, strokeColor: params.region.itemStyle.areaColor,
strokeWeight: 1, fillColor: "#ffffff",fillOpacity: 1
}); //建立多边形覆盖物
map.addOverlay(ply); //添加覆盖物
pointDataay = pointDataay.concat(ply.getPath());
}
map.setViewport(pointDataay); //调整视野
//添加文本标注
if(_this.pointData.length) {
_this.pointData.forEach((item)=>{
_this.addMakerText(map,item.name,item.center)
})
}
//添加标注点
_this.addMarker(map,_this.pointData)
});
},
//添加区县文本标注
addMakerText(map,name,center){
var opts = {
position: new BMap.Point(center[0], center[1]), // 指定文本标注所在的地理位置
offset: new BMap.Size(0, 0) // 设置文本偏移量
};
// 创建文本标注对象
var label = new BMap.Label(name, opts);
// 自定义文本标注样式
label.setStyle({
color: '#333',
border:'none',
background:'none',
padding: '10px',
fontSize: '16px',
height: '30px',
lineHeight: '30px',
fontFamily: '微软雅黑'
});
map.addOverlay(label);
},
//添加区县图片标注点
addMarker(map,pointData) {
let _this = this
let points = pointData
//循环建立标注点
for(var i=0, pointsLen = points.length; i<pointsLen; i++) {
var point = new BMap.Point(Number(points[i].center[0]), Number(points[i].center[1])); //将标注点转化成地图上的点
var myIcon = new BMap.Icon(_this.icon, new BMap.Size(15, 15), {
imageSize: new BMap.Size(15, 15) // 设置图片偏移
});
var marker = new BMap.Marker(point,{icon: myIcon})
if(points[i].alarmState){
var plex = new MapMaker(point,marker); // 创建标
map.addOverlay(plex); //将标注点添加到地图上
}else{
map.addOverlay(marker); //将标注点添加到地图上
}
//添加监听事件
(function() {
var thePoint = points[i];
marker.addEventListener("click",
//显示信息的方法
function() {
_this.getInfo(thePoint.id,(res)=>{
_this.showInfo(this,res,thePoint);
})
}
);
marker.addEventListener("mouseover",
//显示信息的方法
function() {
_this.getInfo(thePoint.id,(res)=>{
_this.showInfo(this,res,thePoint);
})
}
);
marker.addEventListener("mouseout",
//显示信息的方法
function() {
map.closeInfoWindow()
}
);
})();
}
},
//显示弹框内容
showInfo(map,res,thePoint) {
// 创建信息窗口
let opts = {
width: 0,
title: res.data.name
};
//获取点的信息
let sContent = `<ul style="padding:0;margin-top:0;margin-bottom:0">`
+`<li style="line-height: 26px;font-size: 1rem;">`
+`<span style="display: inline-block;">内容:</span>` + `${res.data.content}`
+`</li>`
+`</ul>`;
let infoWindow = new BMap.InfoWindow(sContent,opts); //创建信息窗口对象
let point = new BMap.Point(Number(thePoint.center[0]), Number(thePoint.center[1]))
map.openInfoWindow(infoWindow,point); //图片加载完后重绘infoWindow
},
//-----------------------------------返回按钮-------------------------
back(){
if(this.areaLeval == 3) {
if(this.addressCode[1]) {
this.areaLeval = 2
this.requestGetCityJSON(this.addressCode[1])
} else {
this.areaLeval = 1
this.requestGetProvinceJSON(this.addressCode[0])
}
} else if(this.areaLeval == 2) {
this.areaLeval = 1
this.requestGetProvinceJSON(this.addressCode[0])
} else if(this.areaLeval == 1) {
this.areaLeval = 0
this.requestGetChinaJson()
}
},
}
}
</script>
style部分
<style>
@import "./Json/js/MapMaker.css";
.container {
position: fixed;
top: 0;
left: 0;
right: 0;
bottom: 0;
background: #123258;
}
#chinaMap {
width: 100%;
height: 100%;
}
.back {
color: #fff;
position: fixed;
top: 10px;
left: 10px;
cursor: pointer;
}
#countyMap {
position: fixed !important;
top: 0;
left: 0;
right: 0;
bottom: 0;
}
.BMap_cpyCtrl {
display: none;
}
.anchorBL {
display: none;
}
</style>
注释:如果引用本文内容,请注明出处