echarts 自定義地圖數(shù)據(jù)

1. 地圖數(shù)據(jù)來源

echarts倉庫里面就有校翔,地圖數(shù)據(jù)不會經(jīng)常改變,沒必要在線獲取浪读,還慢
地圖數(shù)據(jù)有jsonjs格式的,jsonecharts壓縮過的,js本質(zhì)就是引入json只是包裝了導(dǎo)出

2. 整形工具

最重要的部分就是利用工具處理這些數(shù)據(jù)节沦,實(shí)現(xiàn)如扣去某塊區(qū)域添加某塊區(qū)域础爬、去除邊界等功能

  1. echarts-mapmaker壓縮解碼地圖數(shù)據(jù)甫贯、合并拆分地圖數(shù)據(jù)
  2. mapshaper整形地圖,主要就是來去除邊界
  3. 文檔看蚜,上面有例子
  4. 這個倉庫也有很多新的地圖數(shù)據(jù)叫搁,自己可以翻看

3. 實(shí)戰(zhàn)

3.1 拆分地圖區(qū)域

這里我們拆分重慶各個區(qū)縣為例

const path = require('path')
const fs = require('fs')
const fsp = require('fs/promises')
const distFolder = path.resolve(__dirname, './dist')
const dest = (fileName) => {
  try {
    fs.accessSync(distFolder, fs.constants.W_OK)
  }catch(err) {
    fs.mkdirSync(distFolder)
  }
  return path.resolve(__dirname, distFolder, fileName)
}

// 引入mapmaker
const maker = require('echarts-mapmaker/src/maker')
// 引入原始地圖數(shù)據(jù)
const chongqingJson = path.resolve(__dirname, './map/province/chongqing.json')
// 解碼地圖數(shù)據(jù)并輸出
// 解碼后的文件就是GeoJson 方便后續(xù)操作
const dec_chonggqing = dest('dec_chongqing.json')
maker.decompress(chongqingJson, dec_chonggqing)
// 分割區(qū)域
maker.splitAsGeojson(dec_chonggqing, distFolder)
解碼后的文件

分割后的文件(名稱是自動根據(jù)json里面的name生成的)

3.2 合并區(qū)域

比如我需要合并中部地區(qū)、西部地區(qū)之類的供炎,就需要合并區(qū)域

// 只需要這一句話
// 合并第一個和第二個json
 maker.merge('./dist/九龍坡區(qū).geojson', './dist/大渡口區(qū).geojson')
根目錄輸出文件

這個方法有些問題:

  1. 無法自定義輸出位置和輸出文件名
  2. 每合并一次輸出文件前面會加一個merge_渴逻,處理起來很麻煩
    可以考慮自己寫一個方法,參考源碼其實(shí)不難(最好還是了解一下geojson
// 源碼
function merge(geojson, geojsonToBeMerged){
  // 讀取兩個文件
  const data = fs.readFileSync(geojson, 'utf8');
  const data2 = fs.readFileSync(geojsonToBeMerged, 'utf8');
  var parent = JSON.parse(data);
  var child = JSON.parse(data2);
  
  // features要素音诫,就是描述邊界信息的一個數(shù)組
  child.features.forEach(function(feature){
    // 只合并不同name的區(qū)域
    parent.features = parent.features.filter((featurex)=>{
      return featurex.properties.name!==feature.properties.name;
    });
    // 直接把一個數(shù)據(jù)的邊界信息放入另一個的features中
    parent.features.push(feature);
  });
  // 寫入文件
  fs.writeFileSync('merged_'+path.basename(geojson), JSON.stringify(parent));
}    

邏輯很簡單惨奕,主要就是提取要素然后放入另一個地圖里面,下面是我簡單的一個封裝

function mergeToOne(targetJSON, distDir, ...childrenJSONList){
  // 讀取目標(biāo)json竭钝,其他json都往這個json合并
  const data = fs.readFileSync(targetJSON, 'utf8');
  const parentData = JSON.parse(data);
  // 循環(huán)需要合并的數(shù)據(jù)
  childrenJSONList.forEach(child => {
    const childJSON= fs.readFileSync(child, 'utf8')
    const childData = JSON.parse(childJSON)
    // 合并
    childData.features.forEach(function(feature){
      parentData.features = parentData.features.filter((featurex)=>{
        return featurex.properties.name!==feature.properties.name;
      });
      parentData.features.push(feature);
    });
  })

  // 寫文件
  fs.writeFileSync(distDir, JSON.stringify(parentData));
}

// 使用
// 最后會輸出一個`合并文件.json`梨撞,合并了三個區(qū)
mergeToOne('./dist/九龍坡區(qū).geojson', './合并文件.json', './dist/大渡口區(qū).geojson', './dist/沙坪壩區(qū).geojson')

3.3 鑲嵌區(qū)域

只用合并也可以,但是在echarts中看起來就不大一樣香罐,使用合并高亮地圖的時候看起來不是一體的卧波,還有其他區(qū)別自行確認(rèn)。
所以還要結(jié)合扣去區(qū)域cut

// 使用 
maker.cut('a.json', '重慶', '沙坪壩區(qū)')

但是源碼似乎有問題穴吹,反正我用開頭給的地圖數(shù)據(jù)是無法正確切除的

// 源碼
var cutAHoleInFeatureAWithFB = (jsonFile, featureA, featureB) => {

  data = fs.readFileSync(jsonFile, 'utf8');

  var geojson = JSON.parse(data);
  var featurea = geojson.features.find(feature => feature.properties.name === featureA);
  var featureb = geojson.features.find(feature => feature.properties.name === featureB);
  // https://stackoverflow.com/questions/43645172/geojson-multipolygon-with-multiple-holes
// 就是這一步 似乎不正確
  featurea.geometry.coordinates.push(featureb.geometry.coordinates[0]);

  fs.writeFileSync("cut_" + jsonFile, JSON.stringify(geojson));
};

查閱資料發(fā)現(xiàn)幽勒,geojson挖去孔洞就是使用MultiPolygon要素,
多邊形帶空洞的數(shù)據(jù)格式是一個四維數(shù)組港令,

{
      "type": "Feature",
      "properties": {},
      "geometry": {
        "type": "MultiPolygon",
        "coordinates":
    [ 
        [
            [
              // 這個就是孔洞的多邊形數(shù)據(jù)
                [101.6455078125,27.68352808378776],
                [114.78515624999999,27.68352808378776],
                [114.78515624999999,35.209721645221386],
                [101.6455078125,35.209721645221386],
                [101.6455078125,27.68352808378776]
            ],
            [
                [104.2822265625,30.107117887092357],
                [108.896484375,30.107117887092357],
                [108.896484375,33.76088200086917],
                [104.2822265625,33.76088200086917],
                [104.2822265625,30.107117887092357]
            
            ]
        ]
    ]
   }
}

// 再簡化
{
  "type": "MultiPolygon",
  "coordinates": [
    [
      {polygon},
      {hole},
      {hole},
      {hole}
    ]
  ]
}

源碼的問題就是

 // coordinates層級錯了
  featurea.geometry.coordinates.push(featureb.geometry.coordinates[0]);
// 改為
featurea.geometry.coordinates[0].push(featureb.geometry.coordinates[0]);

下面是我修改后的

var cutArea = (jsonFile, featureA, featureB) => {

  data = fs.readFileSync(jsonFile, 'utf8');

  var geojson = JSON.parse(data);
  var featurea = geojson.features.find(feature => feature.properties.name === featureA);
  var featureb = geojson.features.find(feature => feature.properties.name === featureB);
  featurea.geometry.coordinates[0].push(featureb.geometry.coordinates[0])
  fs.writeFileSync("cut_" + jsonFile, JSON.stringify(geojson));
}

所以鑲嵌的過程就是:

  1. 合并兩個地圖
  2. 扣去鑲嵌的區(qū)域
mergeToOne('./dist/d_china.json', './合并文件.json', './dist/沙坪壩區(qū).geojson')
cutArea('合并文件.json', '重慶', '沙坪壩區(qū)')

3.4 消除內(nèi)部邊界

主要用到mapshaper啥容,挺復(fù)雜的一個東西,有時間可以詳細(xì)研究

const maker = require('echarts-mapmaker/src/maker')
const shaper = require('mapshaper')
shaper.runCommands('./dist/d_chongqing.json  -dissolve2 -o chongqing_shape_only.geojson', (err) => {
  if(!err) {
    maker.transform('./chongqing_shape_only.geojson', './chongqing_shape_only.echarts.json', '重慶市')
  }
})
  1. 主要利用mapshaperdissolve2命令
  2. 去除邊界完成后echarts不能直接使用顷霹,要用mapmaker轉(zhuǎn)化一次咪惠,這里和掛網(wǎng)的文檔不一樣注意使用transform方法
  3. 官網(wǎng)文檔使用的是全局安裝mapshaper然后用命令行,我這里用的是wiki上的變成方式淋淀,本質(zhì)上也是命令行遥昧。

4 總結(jié)

以上就是基本的一些操作,通過結(jié)合上面的基本方法,我們可以隨意組合想要的地圖數(shù)據(jù)炭臭。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
禁止轉(zhuǎn)載永脓,如需轉(zhuǎn)載請通過簡信或評論聯(lián)系作者。
  • 序言:七十年代末鞋仍,一起剝皮案震驚了整個濱河市常摧,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌威创,老刑警劉巖落午,帶你破解...
    沈念sama閱讀 207,113評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異肚豺,居然都是意外死亡溃斋,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,644評論 2 381
  • 文/潘曉璐 我一進(jìn)店門吸申,熙熙樓的掌柜王于貴愁眉苦臉地迎上來梗劫,“玉大人,你說我怎么就攤上這事呛谜≡谔” “怎么了?”我有些...
    開封第一講書人閱讀 153,340評論 0 344
  • 文/不壞的土叔 我叫張陵隐岛,是天一觀的道長。 經(jīng)常有香客問我瓷翻,道長聚凹,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 55,449評論 1 279
  • 正文 為了忘掉前任齐帚,我火速辦了婚禮妒牙,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘对妄。我一直安慰自己湘今,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 64,445評論 5 374
  • 文/花漫 我一把揭開白布剪菱。 她就那樣靜靜地躺著摩瞎,像睡著了一般。 火紅的嫁衣襯著肌膚如雪孝常。 梳的紋絲不亂的頭發(fā)上旗们,一...
    開封第一講書人閱讀 49,166評論 1 284
  • 那天,我揣著相機(jī)與錄音构灸,去河邊找鬼上渴。 笑死,一個胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的稠氮。 我是一名探鬼主播曹阔,決...
    沈念sama閱讀 38,442評論 3 401
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼隔披!你這毒婦竟也來了次兆?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 37,105評論 0 261
  • 序言:老撾萬榮一對情侶失蹤锹锰,失蹤者是張志新(化名)和其女友劉穎芥炭,沒想到半個月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體恃慧,經(jīng)...
    沈念sama閱讀 43,601評論 1 300
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡园蝠,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,066評論 2 325
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了痢士。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片彪薛。...
    茶點(diǎn)故事閱讀 38,161評論 1 334
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖怠蹂,靈堂內(nèi)的尸體忽然破棺而出善延,到底是詐尸還是另有隱情,我是刑警寧澤城侧,帶...
    沈念sama閱讀 33,792評論 4 323
  • 正文 年R本政府宣布易遣,位于F島的核電站,受9級特大地震影響嫌佑,放射性物質(zhì)發(fā)生泄漏豆茫。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,351評論 3 307
  • 文/蒙蒙 一屋摇、第九天 我趴在偏房一處隱蔽的房頂上張望揩魂。 院中可真熱鬧,春花似錦炮温、人聲如沸火脉。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,352評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽倦挂。三九已至,卻和暖如春白修,著一層夾襖步出監(jiān)牢的瞬間妒峦,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 31,584評論 1 261
  • 我被黑心中介騙來泰國打工兵睛, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留肯骇,地道東北人窥浪。 一個月前我還...
    沈念sama閱讀 45,618評論 2 355
  • 正文 我出身青樓,卻偏偏與公主長得像笛丙,于是被迫代替她去往敵國和親漾脂。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 42,916評論 2 344

推薦閱讀更多精彩內(nèi)容