From 660021a28de9b84b4362c171fdbbf89587f0c5af Mon Sep 17 00:00:00 2001 From: riku <risaku@163.com> Date: 星期四, 13 二月 2025 17:30:50 +0800 Subject: [PATCH] 1. 修改部分bug 2. 新增2D路线轨迹绘制 --- test/grid_test_data.js | 112 ++++++++++++ src/components/mission/MissionEdit.vue | 43 +++- src/views/historymode/HistoryMode.vue | 8 src/views/satellitetelemetry/SatelliteTelemetry.vue | 40 ++++ src/utils/map/grid.js | 52 +++++ src/api/missionApi.js | 4 src/components.d.ts | 2 src/components/mission/MissionManage.vue | 27 +- src/utils/map/calculate.js | 19 ++ src/views/HomePage.vue | 5 src/utils/map/marks.js | 2 src/components/monitor/DataTable.vue | 2 src/utils/color.js | 30 +++ src/stores/mission.js | 2 src/utils/map/line.js | 44 ++++ src/constant/checkbox-options.js | 5 src/constant/checkbox-options/options.js | 91 ++++++++++ 17 files changed, 457 insertions(+), 31 deletions(-) diff --git a/src/api/missionApi.js b/src/api/missionApi.js index d33ebf0..5d881ba 100644 --- a/src/api/missionApi.js +++ b/src/api/missionApi.js @@ -15,6 +15,10 @@ return $http.post(`air/mission/create`, mission).then((res) => res.data); }, + updateMission(mission) { + return $http.post(`air/mission/update`, mission).then((res) => res.data); + }, + deleteMission(missionCode) { let params = `missionCode=${missionCode}`; return $http.post(`air/mission/delete?${params}`).then((res) => res.data); diff --git a/src/components.d.ts b/src/components.d.ts index 11c6829..bdf25d1 100644 --- a/src/components.d.ts +++ b/src/components.d.ts @@ -56,7 +56,7 @@ MapScene: typeof import('./components/map/MapScene.vue')['default'] MapToolbox: typeof import('./components/map/MapToolbox.vue')['default'] MessageBox: typeof import('./components/MessageBox.vue')['default'] - MissionCreate: typeof import('./components/mission/MissionCreate.vue')['default'] + MissionEdit: typeof import('./components/mission/MissionEdit.vue')['default'] MissionImport: typeof import('./components/mission/MissionImport.vue')['default'] MissionManage: typeof import('./components/mission/MissionManage.vue')['default'] OptionDevice: typeof import('./components/search/OptionDevice.vue')['default'] diff --git a/src/components/mission/MIssionCreate.vue b/src/components/mission/MissionEdit.vue similarity index 86% rename from src/components/mission/MIssionCreate.vue rename to src/components/mission/MissionEdit.vue index c7d00f8..c8695b7 100644 --- a/src/components/mission/MIssionCreate.vue +++ b/src/components/mission/MissionEdit.vue @@ -1,12 +1,5 @@ <template> - <el-button - type="primary" - class="el-button-custom" - @click="dialogVisible = !dialogVisible" - > - 鏂板缓浠诲姟 - </el-button> - <CardDialog v-model="dialogVisible" title="鏂板缓璧拌埅浠诲姟"> + <CardDialog v-model="visible" title="鏂板缓璧拌埅浠诲姟"> <el-form :inline="false" :model="formObj" @@ -50,6 +43,22 @@ </el-form-item> </el-form> </CardDialog> + <el-button + v-if="mode == 'create'" + type="primary" + class="el-button-custom" + @click="visible = !visible" + > + 鏂板缓浠诲姟 + </el-button> + <el-button + v-else + type="primary" + size="small" + icon="EditPen" + class="el-button-custom" + @click="visible = !visible" + ></el-button> </template> <script setup> import moment from 'moment'; @@ -60,8 +69,20 @@ import { useFetchData } from '@/composables/fetchData'; import { useMissionStore } from '@/stores/mission'; +const props = defineProps({ + // 璧拌埅浠诲姟缂栬緫妯″紡锛屾柊寤烘垨鏇存柊 + mode: { + type: String, + default: 'create' + } + // visible: { + // type: String, + // default: 'create' + // } +}); + const missionStore = useMissionStore(); -const dialogVisible = ref(false); +const visible = ref(false); const { loading, fetchData } = useFetchData(); const rules = reactive({ location: [ @@ -113,7 +134,7 @@ function createMission() { fetchData((page, pageSize) => { return missionApi.putNewMission(param.value).then((res) => { - dialogVisible.value = false; + visible.value = false; missionStore.fetchMission(); // 閫氱煡鏈嶅姟绔惎鍔ㄤ换鍔¤寖鍥村唴鐨勭涓夋柟鏁版嵁鑾峰彇浠诲姟 thirdPartyDataApi.fetchMissionData(param.value.missionCode); @@ -126,7 +147,7 @@ }, cancel: { do: () => { - dialogVisible.value = false; + visible.value = false; } } }); diff --git a/src/components/mission/MissionManage.vue b/src/components/mission/MissionManage.vue index a385a6e..5695155 100644 --- a/src/components/mission/MissionManage.vue +++ b/src/components/mission/MissionManage.vue @@ -21,7 +21,7 @@ :show-overflow-tooltip="true" border height="64vh" - row-class-name="t-row" + row-class-name="t-row-normal" cell-class-name="t-cell" header-row-class-name="t-header-row" header-cell-class-name="t-header-cell" @@ -38,41 +38,44 @@ label="寮�濮嬫椂闂�" align="center" :formatter="timeFormatter" + width="150" /> <el-table-column prop="endTime" label="缁撴潫鏃堕棿" align="center" :formatter="timeFormatter" + width="150" /> - <el-table-column label="绠$悊" width="140" align="center"> + <el-table-column label="绠$悊" width="160" align="center"> <template #default="{ row }"> + <MissionEdit mode="update"></MissionEdit> <el-button type="primary" size="small" + icon="Delete" class="el-button-custom" @click="deleteMission(row)" - >鍒犻櫎</el-button - > + ></el-button> <el-button :loading="row.downloadLoading" type="primary" size="small" + icon="Document" class="el-button-custom" @click="downloadReport(row)" - >鎶ュ憡</el-button - > + ></el-button> </template> </el-table-column> </el-table> </el-col> <el-col :span="4" class="flex-col"> - <div> - <!-- <el-button type="primary" class="el-button-custom"> + <!-- <div> --> + <!-- <el-button type="primary" class="el-button-custom"> 鏂板缓浠诲姟 </el-button> --> - <MissionCreate></MissionCreate> - </div> + <MissionEdit></MissionEdit> + <!-- </div> --> <!-- <div> <el-button type="primary" class="el-button-custom"> 鏁版嵁瀵煎叆 @@ -166,4 +169,8 @@ .mission-table { /* height: 60vh; */ } + +:deep(.t-row-normal) { + background-color: transparent !important; +} </style> diff --git a/src/components/monitor/DataTable.vue b/src/components/monitor/DataTable.vue index 6579e51..c918ade 100644 --- a/src/components/monitor/DataTable.vue +++ b/src/components/monitor/DataTable.vue @@ -177,7 +177,7 @@ // } // }, tableColumn() { - return checkboxOptions(this.deviceType); + return checkboxOptions(this.deviceType, true); } }, methods: { diff --git a/src/constant/checkbox-options.js b/src/constant/checkbox-options.js index fa3108d..e3d5327 100644 --- a/src/constant/checkbox-options.js +++ b/src/constant/checkbox-options.js @@ -1,6 +1,7 @@ import { TYPE0, TYPE1, TYPE2, TYPE4 } from '@/constant/device-type'; import { option1, + option1All, default1, option2, option3, @@ -13,7 +14,7 @@ } from '@/constant/checkbox-options/options-jingan'; // 鐩戞祴鍥犲瓙鍗曢�夋閫夐」 -function checkboxOptions(deviceType) { +function checkboxOptions(deviceType, allOptions) { if (import.meta.env.VITE_DATA_MODE == 'jingan') { switch (deviceType) { case TYPE0: @@ -24,7 +25,7 @@ } else { switch (deviceType) { case TYPE0: - return option1; + return allOptions ? option1All : option1; case TYPE1: return option3; case TYPE2: diff --git a/src/constant/checkbox-options/options.js b/src/constant/checkbox-options/options.js index f41fac0..9bfd565 100644 --- a/src/constant/checkbox-options/options.js +++ b/src/constant/checkbox-options/options.js @@ -71,6 +71,95 @@ // } ]; +const option1All = [ + { + label: 'NO2', + name: 'NO2', + value: '1' + }, + { + label: 'CO', + name: 'CO', + value: '2' + }, + { + label: 'H2S', + name: 'H2S', + value: '3' + }, + { + label: 'SO2', + name: 'SO2', + value: '4' + }, + { + label: 'O3', + name: 'O3', + value: '5' + }, + { + label: 'PM2.5', + name: 'PM25', + value: '6' + }, + { + label: 'PM10', + name: 'PM10', + value: '7' + }, + { + label: '娓╁害', + name: 'TEMPERATURE', + value: '8' + }, + { + label: '婀垮害', + name: 'HUMIDITY', + value: '9' + }, + { + label: 'TVOC', + name: 'VOC', + value: '10' + }, + + // { + // label: "NOI", + // name: "NOI", + // value: "11" + // }, + { + label: '缁忓害', + name: 'LNG', + value: '12' + }, + { + label: '绾害', + name: 'LAT', + value: '13' + }, + { + label: '杞﹂��', + name: 'VELOCITY', + value: '14' + }, + { + label: '椋庨��', + name: 'WIND_SPEED', + value: '16' + }, + { + label: '椋庡悜', + name: 'WIND_DIRECTION', + value: '17' + } + // { + // label: '楂樺害', + // name: 'HEIGHT', + // value: '18' + // } +]; + // 榛樿閫夐」 const default1 = [option1[5].value, option1[6].value, option1[7].value]; @@ -181,4 +270,4 @@ } ]; -export { option1, default1, option2, option3, default3, option4 }; +export { option1, option1All, default1, option2, option3, default3, option4 }; diff --git a/src/stores/mission.js b/src/stores/mission.js index 37c2871..b90e8e2 100644 --- a/src/stores/mission.js +++ b/src/stores/mission.js @@ -6,7 +6,7 @@ // 璧拌埅浠诲姟 export const useMissionStore = defineStore('mission', () => { const missionList = ref([]); - const { loading, fetchData } = useFetchData(); + const { loading, fetchData } = useFetchData(1000); function fetchMission(type) { return fetchData((page, pageSize) => { diff --git a/src/utils/color.js b/src/utils/color.js new file mode 100644 index 0000000..03a6ced --- /dev/null +++ b/src/utils/color.js @@ -0,0 +1,30 @@ +//杞寲棰滆壊 +function getHexColor(values) { + // 浼犵殑color椤讳负瀛楃涓� + // var values = color + // .replace(/rgba?\(/, '') // 鎶� "rgba(" 鍘绘帀锛屽彉鎴� "194, 7, 15, 1)" + // .replace(/\)/, '') // 鎶� ")" 鍘绘帀锛屽彉鎴� "194, 7, 15, 1" + // .replace(/[\s+]/g, '') // 鎶婄┖鏍煎幓鎺夛紝鍙樻垚 "194,7,15,1" + // .split(',') // 鍙樻垚鏁扮粍 [194,7,15,1] + var a = parseFloat(values[3] || 1), // values[3]鏄痳gba涓殑a鍊硷紝娌℃湁鐨勮瘽璁剧疆a涓�1锛宎鍙兘涓哄皬鏁帮紝鎵�浠ョ敤parseFloat鍑芥暟 + r = Math.floor(a * parseInt(values[0]) + (1 - a) * 255), // 杞崲涓�16杩涘埗 + g = Math.floor(a * parseInt(values[1]) + (1 - a) * 255), + b = Math.floor(a * parseInt(values[2]) + (1 - a) * 255); + return ( + '#' + + ('0' + r.toString(16)).slice(-2) + // 杞崲鍚庣殑16杩涘埗鍙兘涓轰竴浣嶏紝姣斿 7 灏辫浆鎹负 7 锛� 15 杞崲涓� f + ('0' + g.toString(16)).slice(-2) + // 褰撲负涓�浣嶇殑鏃跺�欏氨鍦ㄥ墠闈㈠姞涓� 0锛� + ('0' + b.toString(16)).slice(-2) + ); // 鑻ユ槸涓轰袱浣嶏紝鍔� 0 鍚庡氨鍙樻垚浜嗕笁浣嶏紝鎵�浠ヨ鐢� slice(-2) 鎴彇鍚庝袱浣� +} + +//璁$畻绾挎�ф笎鍙樼殑涓棿棰滆壊鍊� +function getColorBetweenTwoColors(colorA, colorB, ratio) { + const r = Math.round((colorB[0] - colorA[0]) * ratio + colorA[0]); + const g = Math.round((colorB[1] - colorA[1]) * ratio + colorA[1]); + const b = Math.round((colorB[2] - colorA[2]) * ratio + colorA[2]); + + return getHexColor([r, g, b, 1]); +} + +export { getHexColor, getColorBetweenTwoColors }; diff --git a/src/utils/map/calculate.js b/src/utils/map/calculate.js index b9ad407..71859bc 100644 --- a/src/utils/map/calculate.js +++ b/src/utils/map/calculate.js @@ -197,5 +197,24 @@ let mglng = Math.round((lng * 2 - lng - dlng) * 1000000) / 1000000; return [mglng, mglat]; } + }, + + //浠嶨PS杞珮寰� + wgs84_To_Gcj02(lon, lat) { + if (out_of_china(lon, lat)) { + return [lon, lat]; + } else { + let dLat = transformlat(lon - 105.0, lat - 35.0); + let dLon = transformlng(lon - 105.0, lat - 35.0); + let radLat = (lat / 180.0) * PI; + let magic = Math.sin(radLat); + magic = 1 - ee * magic * magic; + let sqrtMagic = Math.sqrt(magic); + dLat = (dLat * 180.0) / (((a * (1 - ee)) / (magic * sqrtMagic)) * PI); + dLon = (dLon * 180.0) / ((a / sqrtMagic) * Math.cos(radLat) * PI); + let mgLat = lat + dLat; + let mgLon = lon + dLon; + return [mgLon, mgLat]; + } } }; diff --git a/src/utils/map/grid.js b/src/utils/map/grid.js new file mode 100644 index 0000000..351bd2c --- /dev/null +++ b/src/utils/map/grid.js @@ -0,0 +1,52 @@ +/** + * 缃戞牸缁樺埗 + */ +import { map } from './index_old'; + +export default { + /** + * 缁樺埗缃戞牸椋庨櫓鍥� + * @param {*} points + */ + drawRectangle: function (points) { + const gridViews = []; + points.forEach((p) => { + const { lb, rt, c } = p; + + // eslint-disable-next-line no-undef + let pList = [lb, rt].map((v) => new AMap.LngLat(v[0], v[1])); + // eslint-disable-next-line no-undef + var bounds = new AMap.Bounds(...pList); + // eslint-disable-next-line no-undef + var rectangle = new AMap.Rectangle({ + bounds: bounds, + // strokeColor: '#ffffffff', + strokeWeight: 0, + strokeOpacity: 0, + // strokeStyle杩樻敮鎸� solid + strokeStyle: 'solid', + fillColor: '990D0D', + fillOpacity: 0.8, + cursor: 'pointer', + zIndex: 50 + }); + + // var text = new AMap.Text({ + // text: p.value, + // anchor: 'center', // 璁剧疆鏂囨湰鏍囪閿氱偣 + // draggable: false, + // style: { + // 'background-color': 'transparent', + // 'border-width': 0, + // 'text-align': 'center', + // 'font-size': '12px', + // color: 'white' + // }, + // position: c + // }); + gridViews.push(rectangle); + // that.textView.push(text); + }); + map.add(gridViews); + } +}; diff --git a/src/utils/map/line.js b/src/utils/map/line.js new file mode 100644 index 0000000..5334f3a --- /dev/null +++ b/src/utils/map/line.js @@ -0,0 +1,44 @@ +import { map } from './index_old'; +import calculate from './calculate'; +import { getHexColor } from '../color'; + +var _polylineArr = []; + +export default { + drawLine(fDatas, factor) { + const lnglats_GD = fDatas.lnglats_GD; + const colors = factor.colors; + + if (_polylineArr) { + map.remove(_polylineArr); + _polylineArr = []; + } + var path = calculate.parse2LngLat(lnglats_GD); + + let sIndex = 0; + for (let i = 1; i < path.length; i++) { + // if (colors[i] == colors[i - 1]) { + // } else { + // } + const _path = [path[i], path[i + 1]]; + const _color = getHexColor(colors[i + 1].map((v) => v * 255)); + // 鍒涘缓鎶樼嚎瀹炰緥 + // eslint-disable-next-line no-undef + const polyline = new AMap.Polyline({ + path: _path, + strokeStyle: 'solid', + isOutline: true, + borderWeight: 2, + outlineColor: 'white', + strokeWeight: 4, // 绾挎潯瀹藉害锛岄粯璁や负 1 + strokeColor: _color, // 绾挎潯棰滆壊 + lineJoin: 'round', // 鎶樼嚎鎷愮偣杩炴帴澶勬牱寮� + showDir: true + }); + _polylineArr.push(polyline); + } + // 灏嗘姌绾挎坊鍔犺嚦鍦板浘瀹炰緥 + map.add(_polylineArr); + return _polylineArr; + } +}; diff --git a/src/utils/map/marks.js b/src/utils/map/marks.js index a72dcdf..03ebbc5 100644 --- a/src/utils/map/marks.js +++ b/src/utils/map/marks.js @@ -25,7 +25,7 @@ for (let i = 0; i < lnglats.length; i++) { data.push({ lnglat: lnglats[i], //鐐规爣璁颁綅缃� - name: `${fDatas.times[i]}<br/>${_factor.factorName}: ${_factor.datas[i].factorData} mg/m鲁`, + name: `${fDatas.times[i]}<br/>${_factor.factorName}: ${_factor.datas[i].factorData} 渭g/m鲁`, id: i }); } diff --git a/src/views/HomePage.vue b/src/views/HomePage.vue index 2e68604..6e0f275 100644 --- a/src/views/HomePage.vue +++ b/src/views/HomePage.vue @@ -4,6 +4,7 @@ <CoreHeader></CoreHeader> <el-row class="dropdown-wrap"> <MapToolbox></MapToolbox> + <!-- <SatelliteTelemetry></SatelliteTelemetry> --> <!-- <MissionManage></MissionManage> --> <ConfigManage></ConfigManage> <!-- <MapLocation></MapLocation> --> @@ -15,7 +16,9 @@ </div> </template> -<script setup></script> +<script setup> +import SatelliteTelemetry from '@/views/satellitetelemetry/SatelliteTelemetry.vue'; +</script> <style scoped> .overlay-container { diff --git a/src/views/historymode/HistoryMode.vue b/src/views/historymode/HistoryMode.vue index 9f9c573..b63cf49 100644 --- a/src/views/historymode/HistoryMode.vue +++ b/src/views/historymode/HistoryMode.vue @@ -49,6 +49,7 @@ <script> import Layer from '@/utils/map/3dLayer'; +import mapLine from '@/utils/map/line'; import marks from '@/utils/map/marks'; import sector from '@/utils/map/sector'; import mapUtil from '@/utils/map/util'; @@ -137,7 +138,8 @@ // 鍒锋柊鍥句緥 const factor = this.factorDatas.factor[this.factorType]; sector.clearSector(); - this.drawRoadMap(factor); + this.drawRoadLine(factor); + // this.drawRoadMap(factor); this.drawMassMarks(factor); }, // 缁樺埗3D璧拌璺嚎鍥� @@ -145,7 +147,9 @@ this.factorDatas.refreshHeight(this.factorType); Layer.drawRoadMap(this.factorDatas, e, this.merge, this.setCenter); - // } + }, + drawRoadLine(e) { + mapLine.drawLine(this.factorDatas, e); }, drawMassMarks(e) { marks.drawMassMarks(this.factorDatas, e, (index) => { diff --git a/src/views/satellitetelemetry/SatelliteTelemetry.vue b/src/views/satellitetelemetry/SatelliteTelemetry.vue new file mode 100644 index 0000000..fd1a40d --- /dev/null +++ b/src/views/satellitetelemetry/SatelliteTelemetry.vue @@ -0,0 +1,40 @@ +<template> + <div class="p-events-auto"> + <el-button type="info" icon="Memo" plain @click="drawGrid"> + 缁樺埗缃戞牸 + </el-button> + </div> +</template> +<script setup> +import calculate from '@/utils/map/calculate'; +import grid from '@/utils/map/grid'; +import { gridData } from '../../../test/grid_test_data'; + +function drawGrid() { + // const points = gridData.map((v) => { + // return calculate.wgs84_To_Gcj02(v[0], v[1]); + // }); + // const p1 = points[0]; + // const p2 = points[1]; + // const diffLng = Math.abs(p1[0] - p2[0]); + // const diffLat = Math.abs(p1[1] - p2[1]); + // const bounds = points.map((v) => { + // return { + // // 涓滅粡锛屽寳绾儏鍐典笅 + // lb: [v[0] - diffLng, v[1] - diffLat], + // rt: [v[0] + diffLng, v[1] - diffLat], + // c: v + // }; + // }); + + const bounds = [ + { + lb: [121.360898, 31.222733], + rt: [121.364898, 31.226733], + c: [121.362898, 31.224733] + } + ]; + + grid.drawRectangle(bounds); +} +</script> diff --git a/test/grid_test_data.js b/test/grid_test_data.js new file mode 100644 index 0000000..5b72b3d --- /dev/null +++ b/test/grid_test_data.js @@ -0,0 +1,112 @@ +const gridData = [ + [121.329723, 31.240625], + [121.339366, 31.241204], + [121.34901, 31.241781], + [121.358654, 31.242358], + [121.368299, 31.242935], + [121.377943, 31.24351], + [121.387588, 31.244085], + [121.397234, 31.244659], + [121.406879, 31.245233], + [121.416525, 31.245805], + [121.426171, 31.246377], + [121.435818, 31.246949], + [121.330396, 31.232339], + [121.340039, 31.232918], + [121.349682, 31.233495], + [121.359325, 31.234072], + [121.368969, 31.234648], + [121.378613, 31.235223], + [121.388257, 31.235798], + [121.397901, 31.236372], + [121.407546, 31.236945], + [121.417191, 31.237518], + [121.426836, 31.23809], + [121.436482, 31.238661], + [121.331069, 31.224054], + [121.340711, 31.224632], + [121.350353, 31.225209], + [121.359996, 31.225786], + [121.369639, 31.226362], + [121.379282, 31.226937], + [121.388925, 31.227511], + [121.398569, 31.228085], + [121.408213, 31.228658], + [121.417857, 31.22923], + [121.427501, 31.229802], + [121.437146, 31.230373], + [121.331742, 31.215768], + [121.341383, 31.216346], + [121.351025, 31.216923], + [121.360666, 31.217499], + [121.370308, 31.218075], + [121.379951, 31.21865], + [121.389593, 31.219224], + [121.399236, 31.219798], + [121.408879, 31.220371], + [121.418522, 31.220943], + [121.428166, 31.221514], + [121.43781, 31.222085], + [121.332415, 31.207482], + [121.342055, 31.20806], + [121.351696, 31.208637], + [121.361337, 31.209213], + [121.370978, 31.209788], + [121.380619, 31.210363], + [121.390261, 31.210937], + [121.399903, 31.211511], + [121.409545, 31.212083], + [121.419188, 31.212655], + [121.42883, 31.213227], + [121.438473, 31.213797], + [121.333087, 31.199196], + [121.342727, 31.199774], + [121.352366, 31.20035], + [121.362006, 31.200926], + [121.371647, 31.201502], + [121.381287, 31.202076], + [121.390928, 31.20265], + [121.400569, 31.203224], + [121.410211, 31.203796], + [121.419853, 31.204368], + [121.429494, 31.204939], + [121.439137, 31.205509], + [121.333759, 31.19091], + [121.343398, 31.191488], + [121.353037, 31.192064], + [121.362676, 31.19264], + [121.372316, 31.193215], + [121.381955, 31.19379], + [121.391595, 31.194363], + [121.401236, 31.194936], + [121.410876, 31.195509], + [121.420517, 31.19608], + [121.430158, 31.196651], + [121.4398, 31.197221], + [121.334431, 31.182624], + [121.344069, 31.183201], + [121.353707, 31.183778], + [121.363345, 31.184354], + [121.372984, 31.184928], + [121.382623, 31.185503], + [121.392262, 31.186076], + [121.401902, 31.186649], + [121.411542, 31.187221], + [121.421182, 31.187793], + [121.430822, 31.188363], + [121.440462, 31.188933], + [121.335103, 31.174338], + [121.34474, 31.174915], + [121.354377, 31.175492], + [121.364015, 31.176067], + [121.373652, 31.176642], + [121.38329, 31.177216], + [121.392929, 31.177789], + [121.402568, 31.178362], + [121.412206, 31.178934], + [121.421846, 31.179505], + [121.431485, 31.180076], + [121.441125, 31.180645] +]; + +export { gridData }; -- Gitblit v1.9.3