Commit d61d4d358399c9289238573d5cb8c328223bc8be

Authored by fengwotao
1 parent 0f13f3c4

feat(src/packages): 图表3d地图也支持下钻 修改地图注册方式为服务端接口请求

... ... @@ -24,7 +24,8 @@ const selectOptions = reactive({
24 24 const selectValues = reactive({
25 25 provinceValue: 'china',
26 26 cityValue: null,
27   - countyValue: null
  27 + countyValue: null,
  28 + levelStr: areaEnum.COUNTRY
28 29 })
29 30
30 31 const getAreaLists = async (level = areaEnum.PROVINCE, parentId = 1) => {
... ... @@ -49,13 +50,15 @@ onMounted(async () => {
49 50 const onHandleSelectProvince = async (value: number | string) => {
50 51 selectValues.cityValue = null
51 52 selectValues.countyValue = null
52   - if (value === 'china') return
  53 + if (value === 'china') return (selectValues.levelStr = areaEnum.COUNTRY)
53 54 selectOptions.cityOptions = await getAreaLists(areaEnum.CITY, value as any)
  55 + selectValues.levelStr = areaEnum.PROVINCE
54 56 }
55 57
56 58 const onHandleSelectCity = async (value: number) => {
57 59 selectValues.countyValue = null
58 60 selectOptions.countryOptions = await getAreaLists(areaEnum.COUNTY, value)
  61 + selectValues.levelStr = areaEnum.CITY
59 62 }
60 63
61 64 const onHandleSubmit = () => {
... ...
... ... @@ -7,9 +7,11 @@ import dataMaps from './data.json'
7 7
8 8 //省市区枚举
9 9 export const enum areaEnum {
10   - PROVINCE = 'PROVINCE',
11   - CITY = 'CITY',
12   - COUNTY = 'COUNTY'
  10 + PROVINCE = 'PROVINCE', //省份
  11 + CITY = 'CITY', //城市
  12 + COUNTY = 'COUNTY', //县
  13 + COUNTRY = 'COUNTRY', //国家
  14 + TOWN = 'TOWN' //镇
13 15 }
14 16
15 17 export const includes = []
... ... @@ -24,34 +26,28 @@ export const option = {
24 26 mapRegion: {
25 27 adcode: 'china',
26 28 showHainanIsLands: true,
27   - saveSelect: {}
  29 + saveSelect: {
  30 + levelStr: areaEnum.COUNTRY
  31 + }
28 32 },
29 33 tooltip: {
30 34 show: true
31 35 },
32 36 geo3D: {
  37 + show: false, // 隐藏该层,为true时会导致出现两个地图
33 38 map: 'centerMap',
34 39 roam: true,
35 40 regionHeight: 0,
36   - label: {
37   - show: true,
38   - textStyle: {
39   - fontSize: 14,
40   - color: 'blue',
41   - borderWidth: 0,
42   - borderColor: '#000'
43   - }
44   - },
45 41 emphasis: {
46 42 label: {
47 43 show: true,
48 44 textStyle: {
49   - color: 'black',
50   - fontSize: 32
  45 + color: '#000',
  46 + fontSize: 14
51 47 }
52 48 },
53 49 itemStyle: {
54   - color: '#fd9c5a'
  50 + color: '#ff0'
55 51 }
56 52 }
57 53 },
... ... @@ -63,8 +59,10 @@ export const option = {
63 59 regionHeight: 3,
64 60 label: {
65 61 show: true,
66   - color: 'yellow',
67   - fontSize: 14
  62 + textStyle: {
  63 + color: '#fff',
  64 + fontSize: 14
  65 + }
68 66 },
69 67 itemStyle: {
70 68 color: 'green',
... ...
... ... @@ -2,7 +2,7 @@
2 2 <!-- Echarts 全局设置 -->
3 3 <global-setting :optionData="optionData"></global-setting>
4 4 <CollapseItem name="地图" :expanded="true">
5   - <!-- <SettingItemBox name="开启下钻">
  5 + <SettingItemBox name="开启下钻">
6 6 <SettingItem name="">
7 7 <n-switch v-model:value="optionData.drillingIn" size="small"></n-switch>
8 8 </SettingItem>
... ... @@ -34,7 +34,7 @@
34 34 placeholder="请输入"
35 35 ></n-input-number>
36 36 </SettingItem>
37   - </SettingItemBox> -->
  37 + </SettingItemBox>
38 38 <SelectCity :optionData="optionData" :drillingIn="optionData.drillingIn" @submit="onHandleSelectValues" />
39 39 <SettingItemBox name="颜色">
40 40 <SettingItem name="区域颜色">
... ... @@ -69,11 +69,15 @@
69 69 <n-switch v-model:value="seriesList[0].label.show" size="small"></n-switch>
70 70 </SettingItem>
71 71 <SettingItem name="颜色">
72   - <n-color-picker size="small" :modes="['hex']" v-model:value="seriesList[0].label.color"></n-color-picker>
  72 + <n-color-picker
  73 + size="small"
  74 + :modes="['hex']"
  75 + v-model:value="seriesList[0].label.textStyle.color"
  76 + ></n-color-picker>
73 77 </SettingItem>
74 78 <SettingItem name="大小">
75 79 <n-input-number
76   - v-model:value="seriesList[0].label.fontSize"
  80 + v-model:value="seriesList[0].label.textStyle.fontSize"
77 81 :min="0"
78 82 size="small"
79 83 placeholder="请输入"
... ...
... ... @@ -4,12 +4,12 @@
4 4 </template>
5 5
6 6 <script setup lang="ts">
7   -import { onMounted, ref, nextTick, PropType, toRefs, watch } from 'vue'
  7 +import { onMounted, ref, nextTick, PropType, toRefs, watch, reactive } from 'vue'
8 8 import * as echarts from 'echarts'
9 9 import { registerMap } from 'echarts/core'
10 10 import 'echarts-gl'
11   -import config from './config'
12   -import cityMap from '../OverrideMapBase/mapGeojson/china-main-city-map.json'
  11 +import config, { areaEnum } from './config'
  12 +import { getGeoJsonMap } from '@/api/external/common'
13 13
14 14 type historyDataType = { name: string; code: string }
15 15
... ... @@ -71,40 +71,76 @@ props.chartConfig.option = {
71 71 }
72 72
73 73 //地图点击返回
74   -const watchAdcode = () => {
  74 +const watchAdcode = async () => {
75 75 if (props.chartConfig.option.drillingIn) {
76   - const code = historyData.value.at(-2)?.code
77   - props.chartConfig.option.mapRegion.adcode = code ? code : 'china'
78   - historyData.value.pop()
  76 + saveLevelStr.level = saveLevelStr.parentInfo.level
  77 + await getGeojson(saveLevelStr.parentInfo.adcode)
  78 + props.chartConfig.option.geo3D.map =
  79 + saveLevelStr.parentInfo.adcode === 100000 ? 'china' : saveLevelStr.parentInfo.adcode
  80 + props.chartConfig.option.series.forEach((item: any) => {
  81 + if (item.type === 'map3D')
  82 + item.map = saveLevelStr.parentInfo.adcode === 100000 ? 'china' : saveLevelStr.parentInfo.adcode
  83 + item.data = props.chartConfig.option.dataset
  84 + })
  85 + handleSetOption(chartInstance.value, props.chartConfig.option)
79 86 }
80 87 }
81 88
  89 +const regionMapParentArea = {
  90 + [areaEnum.PROVINCE]: areaEnum.COUNTRY, //省份的上一级 中国
  91 + [areaEnum.CITY]: areaEnum.PROVINCE, //城市的上一级 省份
  92 + [areaEnum.COUNTY]: areaEnum.CITY, //县或者区的上一级 城市
  93 + [areaEnum.TOWN]: areaEnum.COUNTY //镇的上一级 县或者区
  94 +}
  95 +
82 96 //地图点击
83 97 const handleMap3DClick = async (params: any) => {
84 98 if (props.chartConfig.option.drillingIn) {
85 99 const { name } = params
86   - saveSelectValue.value = name
87   - const findAdcode = (cityMap as any)[name]
88   - if (!findAdcode) return
89   - props.chartConfig.option.mapRegion.adcode = findAdcode
90   - historyData.value.push({
91   - name,
92   - code: findAdcode
  100 + saveGeojson.value?.features.forEach((item: any) => {
  101 + if (item.properties.name === name) {
  102 + const level = item.properties.level.toUpperCase()
  103 + const adcode = item.properties.adcode
  104 + props.chartConfig.option.mapRegion.adcode = adcode
  105 + saveLevelStr.level = level
  106 + saveLevelStr.parentInfo.adcode = item.properties.parent.adcode //保存上一级的地区编码
  107 + saveLevelStr.parentInfo.level = (regionMapParentArea as any)[level] //保存上一级的行政级别
  108 + }
93 109 })
94 110 }
95 111 }
96 112
  113 +const saveGeojson: any = ref({}) // 保存geojson
  114 +
  115 +const chinaDefaultRegionId = ref(100000) //如果是china则adcode为100000
  116 +
  117 +const saveLevelStr = reactive({
  118 + // 保存行政级别和上一级的adcode和level
  119 + level: '',
  120 + parentInfo: {
  121 + adcode: 0,
  122 + level: ''
  123 + }
  124 +})
  125 +
97 126 //动态获取geojson文件进行注册地图
98   -const getGeojson = (regionId: string) => {
  127 +const getGeojson = (regionId: any) => {
99 128 try {
100 129 return new Promise<boolean>(resolve => {
101   - import(`../OverrideMapBase/mapGeojson/${regionId}.json`).then(data => {
102   - registerMap(regionId, { geoJSON: data.default as any, specialAreas: {} })
  130 + const { levelStr } = props.chartConfig.option.mapRegion.saveSelect //右侧配置项获取的行政级别
  131 + getGeoJsonMap(
  132 + regionId === 'china' ? chinaDefaultRegionId.value : regionId,
  133 + !saveLevelStr.level ? levelStr : saveLevelStr.level
  134 + ).then(res => {
  135 + const { geoJson, name, code, level } = res.data
  136 + const geoJsonFile = JSON.parse(geoJson)
  137 + saveGeojson.value = geoJsonFile
  138 + registerMap(level === areaEnum.COUNTRY ? name : code, { geoJSON: geoJsonFile as any, specialAreas: {} })
103 139 resolve(true)
104 140 })
105 141 })
106   - } catch (e) {
107   - console.log(e)
  142 + } catch (error) {
  143 + console.error('注册地图出错', error)
108 144 }
109 145 }
110 146
... ... @@ -126,8 +162,7 @@ const initMap = async () => {
126 162 handleSetOption(chartInstance.value, props.chartConfig.option)
127 163 })
128 164 chartInstance.value.on('click', (e: any) => {
129   - console.log(`地图点击`, e)
130   - // handleMap3DClick(e)
  165 + handleMap3DClick(e)
131 166 })
132 167 }
133 168
... ... @@ -137,8 +172,8 @@ const handleSetOption = (instance: any, option: any) => {
137 172 try {
138 173 instance.clear()
139 174 instance.setOption(option)
140   - // eslint-disable-next-line no-empty
141   - } finally {
  175 + } catch (error) {
  176 + console.error('触发渲染出错', error)
142 177 }
143 178 }
144 179
... ... @@ -161,7 +196,7 @@ watch(
161 196 })
162 197 handleSetOption(chartInstance.value, props.chartConfig.option)
163 198 } catch (error) {
164   - console.log(error)
  199 + console.log('展示区域发生变化出错', error)
165 200 }
166 201 },
167 202 {
... ...
... ... @@ -152,7 +152,7 @@ const getGeojson = async (regionId: any) => {
152 152 }
153 153
154 154 //异步时先注册空的 保证初始化不报错
155   -registerMap(`${props.chartConfig.option.mapRegion.adcode}`, { geoJSON: {} as any, specialAreas: {} })
  155 +registerMap(props.chartConfig.option.mapRegion.adcode, { geoJSON: {} as any, specialAreas: {} })
156 156
157 157 // 进行更换初始化地图 如果为china 单独处理
158 158 const registerMapInitAsync = async () => {
... ...