地图渲染

步骤:

  1. 通过 DataV.GeoAtlas地理小工具系列 网站获取到数据
  2. registerMap注册地图
  3. 初始化图表
  4. 配置echarts地理坐标系组件, 配置要渲染的数据
示意图 示意图
效果图
效果图
tooltip内容自定义
tooltip内容自定义

核心代码如下,更多代码详细见仓库: https://gitee.com/whongli/map

import * as echarts from 'echarts'
import {httpGet} from '@/js/api/baseApi'
var chinaMap

export default {
  methods: {
    async init ({url, option}) {
      let res = await httpGet(url) // 获取地图数据
      let chinaJson = res
      echarts.registerMap('china', chinaJson)
      chinaMap = echarts.init(document.getElementById('china-map'))
      chinaMap.setOption(option)
      chinaMap.on('click', async (params) => {
        console.log(params)
        this.$router.push(`/province?name=${params.name}`)
      })
    },
    async provinceInit ({url, option}) {
      let res = await httpGet(url)
      let chinaJson = res
      echarts.registerMap('china', chinaJson)
      chinaMap = echarts.init(document.getElementById('china-map'))
      chinaMap.setOption(option)
      chinaMap.on('click', async (params) => {
        console.log(params)
        // TODO: 省市点击回调
      })
    },
    /**
     * 地图配置
     * @param {*} series {data,title,zoom, tooltip, center}
     * @returns 返回配置信息
     */
    constructorOption (series) {
      return {
        backgroundColor: '#fff',
        // 地图上圆点的提示
        tooltip: {
          trigger: 'item',
          formatter: function (params) {
            console.log(params)
            return params.name + ' : ' + params.value[2]
          }
        },
        // 图例按钮 点击可选择哪些不显示
        legend: {
          orient: 'vertical',
          left: 'left',
          top: 'bottom',
          data: [],
          textStyle: {
            color: '#fff'
          }
        },
        // 地理坐标系组件
        geo: {
          map: 'china',
          zoom: series.zoom || 1.25, // 设置初始化的缩放比例
          roam: false, // true 允许缩放拖动
          center: series.center || [104.123557, 32.058039],
          label: {
            // true hover时地图内部会显示城市名
            emphasis: {
              show: false
            }
          },
          tooltip: series.tooltip || {
            show: true,
            trigger: 'item',
            formatter: function (params) {
              console.log(params)
              let html = `

地区: ${params.name}

人口:46万(人) ${params.name}

旅游人数:6万(人) ${params.name}

` return html } }, itemStyle: { // 地图背景色 normal: { areaColor: '#fff', borderColor: '#747569' }, // 悬浮时 emphasis: { areaColor: '#c82a29', borderColor: '#c82a29' } }, regions: [{ // 省份颜色与界线颜色的修改,如果想修改多个省份就在后面多添加几个对象即可. // name: '广东', // 对应的是import './china' 数据中的名称如: name: '广东' // itemStyle: { // normal: { // borderColor: '#c82a29', // 省份界线颜色 // borderWidth: 1 // 省份界线的宽度 // } // } }] }, // 系列列表 series: [ { name: series.name, type: 'effectScatter', coordinateSystem: 'geo', data: series.data, // 从方法中传进来 symbolSize: 8, // 点的大小 symbol: 'circle', label: { normal: { show: false }, emphasis: { show: false } }, // 涟漪特效相关配置 rippleEffect: { color: '#c82a29', period: 4, scale: 2, brushType: 'fill', // stroke | fill number: 2 }, showEffectOn: 'render', itemStyle: { normal: { color: { type: 'radial', colorStops: [ { offset: 1, color: '#c82a29' } ], global: false // 缺省为 false } } } } ] } } } }
  1. 直接下载的地图数据文件比较大,可做压缩处理,控制台执行 node minify-map-data.js,压缩代码参考 echart源码-encode.js
// minify-map-data.js
var fs = require('fs');
var glob = require('glob');

glob('static/map-data/*.json', {}, function (err, files) {
  files.forEach(function (file) {
    // 这里有做修改
    var output = file.replace('map-data', 'minify-map');
    var rawStr = fs.readFileSync(file, 'utf8');
    var json = JSON.parse(rawStr);
    // Meta tag
    json.UTF8Encoding = true;
    var features = json.features;
    if (!features) {
      return;
    }
    features.forEach(function (feature) {
      var encodeOffsets = feature.geometry.encodeOffsets = [];
      var coordinates = feature.geometry.coordinates;
      if (feature.geometry.type === 'Polygon') {
        coordinates.forEach(function (coordinate, idx) {
          coordinates[idx] = encodePolygon(
            coordinate, encodeOffsets[idx] = []
          );
        });
      } else if (feature.geometry.type === 'MultiPolygon') {
        coordinates.forEach(function (polygon, idx1) {
          encodeOffsets[idx1] = [];
          polygon.forEach(function (coordinate, idx2) {
            coordinates[idx1][idx2] = encodePolygon(
              coordinate, encodeOffsets[idx1][idx2] = []
            );
          });
        });
      }
    });
    // 这里有做修改
    fs.writeFileSync(
      output, JSON.stringify(json), 'utf8'
    );
  });
});

function encodePolygon(coordinate, encodeOffsets) {
  var result = '';

  var prevX = quantize(coordinate[0][0]);
  var prevY = quantize(coordinate[0][1]);
  // Store the origin offset
  encodeOffsets[0] = prevX;
  encodeOffsets[1] = prevY;

  for (var i = 0; i < coordinate.length; i++) {
    var point = coordinate[i];
    result += encode(point[0], prevX);
    result += encode(point[1], prevY);

    prevX = quantize(point[0]);
    prevY = quantize(point[1]);
  }

  return result;
}
// 这个方法我没用
function addAMDWrapper(jsonStr) {
  return ['define(function() {',
    '    return ' + jsonStr + ';',
    '});'].join('\n');
}

function encode(val, prev) {
  // Quantization
  val = quantize(val);
  // var tmp = val;
  // Delta
  val = val - prev;

  if (((val << 1) ^ (val >> 15)) + 64 === 8232) {
    //WTF, 8232 will get syntax error in js code
    val--;
  }
  // ZigZag
  val = (val << 1) ^ (val >> 15);
  // add offset and get unicode
  return String.fromCharCode(val + 64);
  // var tmp = {'tmp' : str};
  // try{
  //     eval("(" + JSON.stringify(tmp) + ")");
  // }catch(e) {
  //     console.log(val + 64);
  // }
}

function quantize(val) {
  return Math.ceil(val * 1024);
}

你可能感兴趣的:(地图渲染)