1
0

mapComponent.tsx 6.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247
  1. import * as echarts from 'echarts';
  2. import styles from './mapComponent.less';
  3. import React, { useEffect, useRef } from 'react';
  4. import border from '../../../public/assets/decoration_six.png';
  5. import * as datav from '@jiaminghi/data-view-react';
  6. interface propsData {
  7. userData: object;
  8. areaList: any;
  9. mapData: any;
  10. }
  11. /**
  12. * 地图组件
  13. * @constructor
  14. */
  15. const MapComponent: React.FC<propsData> = (props) => {
  16. const chartRef: any = useRef();
  17. const { userData, areaList, mapData } = props;
  18. const data: any = mapData.map_json; //地图的数据来自之前引入的json文件
  19. const geoCoordMap = {
  20. 济南市: [117, 36.65],
  21. 青岛市: [120.33, 36.07],
  22. 淄博市: [118.05, 36.78],
  23. 枣庄市: [117.57, 34.86],
  24. 东营市: [118.49, 37.46],
  25. 烟台市: [121.39, 37.52],
  26. 潍坊市: [119.1, 36.62],
  27. 济宁市: [116.59, 35.38],
  28. 泰安市: [117.13, 36.18],
  29. 威海市: [122.1, 37.5],
  30. 日照市: [119.46, 35.42],
  31. 临沂市: [118.35, 35.05],
  32. 德州市: [116.29, 37.45],
  33. 聊城市: [115.97, 36.45],
  34. 滨州市: [118.03, 37.36],
  35. 菏泽市: [115.47, 35.25],
  36. };
  37. // 处理数据结构
  38. const convertData = (item: string | any[]) => {
  39. const res = [];
  40. for (let i = 0; i < item.length; i++) {
  41. const geoCoord = geoCoordMap[item[i].name];
  42. if (geoCoord) {
  43. res.push({
  44. name: item[i].name,
  45. value: geoCoord.concat(item[i].value),
  46. });
  47. }
  48. }
  49. return res;
  50. };
  51. useEffect(() => {
  52. const myChart = echarts.init(chartRef.current);
  53. echarts.registerMap('shandong', data); //此步不可省略,要想展示一个地图,先需要注册,巨坑(官方根本无文档,全靠瞎猜,气死我了快)
  54. // 点位
  55. // const points = [];
  56. // // 线
  57. // const lineData = [];
  58. // for(let i=0;i<Object.keys(geoCoordMap).length;i++){
  59. // points.push({
  60. // name:Object.keys(geoCoordMap)[i],
  61. // value:geoCoordMap[Object.keys(geoCoordMap)[i]]
  62. // })
  63. // lineData.push({
  64. // name:`济南 -> ${Object.keys(geoCoordMap)[i]}`,
  65. // value: 40,
  66. // coords: [
  67. // [117, 36.65],
  68. // geoCoordMap[Object.keys(geoCoordMap)[i]]
  69. // ]
  70. // })
  71. // }
  72. // const colors = ['#46bee9'];
  73. const options = {
  74. geo: {
  75. show: true,
  76. map: 'shandong',
  77. roam: false,
  78. zoom: 1.2,
  79. label: {
  80. normal: {
  81. show: false,
  82. },
  83. emphasis: {
  84. show: false,
  85. },
  86. },
  87. itemStyle: {
  88. normal: {
  89. areaColor: '#091632',
  90. borderColor: '#1773c3',
  91. shadowColor: '#1773c3',
  92. shadowBlur: 20,
  93. },
  94. },
  95. },
  96. series: [
  97. {
  98. name: 'light',
  99. type: 'scatter',
  100. coordinateSystem: 'geo',
  101. data: convertData(areaList),
  102. symbolSize: function (val: number[]) {
  103. return val[2];
  104. },
  105. label: {
  106. normal: {
  107. formatter: '{b}',
  108. position: 'right',
  109. show: true,
  110. },
  111. emphasis: {
  112. show: true,
  113. },
  114. },
  115. itemStyle: {
  116. normal: {
  117. color: '#ddb926',
  118. },
  119. },
  120. },
  121. {
  122. type: 'map',
  123. map: 'shandong',
  124. zoom: 1.2,
  125. label: {
  126. normal: {
  127. show: false,
  128. },
  129. emphasis: {
  130. show: false,
  131. textStyle: {
  132. color: '#fff',
  133. },
  134. },
  135. },
  136. roam: false,
  137. itemStyle: {
  138. normal: {
  139. areaColor: '#031525',
  140. borderColor: '#3B5077',
  141. borderWidth: 1,
  142. },
  143. emphasis: {
  144. areaColor: '#0f2c70',
  145. },
  146. },
  147. data: [],
  148. },
  149. // {
  150. // type: 'effectScatter',
  151. // coordinateSystem: 'geo',
  152. // showEffectOn: 'render',
  153. // rippleEffect: {
  154. // period: 5,
  155. // scale: 5,
  156. // brushType: 'fill'
  157. // },
  158. // hoverAnimation: true,
  159. // label: {
  160. // formatter: '{b}',
  161. // position: 'right',
  162. // offset: [15, 0],
  163. // color: (param: { dataIndex: number; }) => colors[param.dataIndex % colors.length],
  164. // show: true
  165. // },
  166. // itemStyle: {
  167. // color: (param: { dataIndex: number; }) => {
  168. // return colors[param.dataIndex % colors.length];
  169. // },
  170. // shadowBlur: 10,
  171. // shadowColor: '#333',
  172. // opacity: 0.75
  173. // },
  174. // emphasis: {
  175. // itemStyle: {
  176. // opacity: 1, //线条宽度
  177. // }
  178. // },
  179. // data: points
  180. // },
  181. // {
  182. // name: '济南',
  183. // type: 'lines',
  184. // zlevel: 2,
  185. // symbol: ['none', 'arrow'],
  186. // symbolSize: 7,
  187. // effect: {
  188. // show: true,
  189. // period: 4,
  190. // trailLength: 0.02,
  191. // symbol: 'circle',
  192. // symbolSize: 4,
  193. // color: '#46bee9'
  194. // },
  195. // lineStyle: {
  196. // width: 0.5, //线条宽度
  197. // opacity: 0.5, //尾迹线条透明度
  198. // curveness: .3, //尾迹线条曲直度
  199. // shadowBlur: 10,
  200. // color: '#46bee9'
  201. // },
  202. // emphasis: {
  203. // lineStyle: {
  204. // width: 2, //线条宽度
  205. // }
  206. // },
  207. // data: lineData
  208. // }
  209. ],
  210. };
  211. myChart.setOption(options, true);
  212. // 组件卸载
  213. return () => {
  214. myChart.clear();
  215. };
  216. }, []);
  217. return (
  218. <div className={styles.container}>
  219. <div ref={chartRef} className={styles.mapContent} />
  220. <div className={styles.content_num}>
  221. <div style={{ position: 'relative' }}>
  222. <img
  223. src={border}
  224. alt="装饰线条"
  225. style={{ width: '200px', height: '95px', transform: 'rotateY(180deg)' }}
  226. />
  227. <div className={styles.content}>
  228. <datav.DigitalFlop
  229. config={userData}
  230. className={styles.content_value}
  231. style={{ width: '200px', height: '50px' }}
  232. />
  233. <div className={styles.content_title}>用户数</div>
  234. </div>
  235. </div>
  236. </div>
  237. </div>
  238. );
  239. };
  240. export default MapComponent;