经验首页 前端设计 程序设计 Java相关 移动开发 数据库/运维 软件/图像 大数据/云计算 其他经验
当前位置:技术经验 » JS/JS库/框架 » jQuery » 查看文章
OpenLayers在地图上显示统计图,饼图线状图柱状图,修复统计图跳动的问题
来源:cnblogs  作者:潇洒今生  时间:2018/12/24 10:31:46  对本文有异议

 

环境介绍
Openlayers ol.js v5.3.0
Highcharts highcharts.js v7.0.1
jquery jquery-3.3.1.js v3.3.1

 

 

 

 

 

显示效果

地图放大缩小对统计图的大小无影响

以饼状图为例

1、添加地图,并渲染统计图所在的点位,

  1. vector是渲染feature需要用的图层,一定要保证在所有图层的最前方,否则渲染的feature会被遮盖,(地图量算时由于这个问题搞了一上午)
  1. sourceMeasure = new ol.source.Vector({ wrapX: false });
  2.  
  3. vector = new ol.layer.Vector({
  4. source: sourceMeasure,
  5. style: new ol.style.Style({
  6. fill: new ol.style.Fill({
  7. color: 'rgba(255, 255, 0, 0.2)'
  8. }),
  9. stroke: new ol.style.Stroke({
  10. color: '#ffcc33',
  11. width: 2
  12. }),
  13. image: new ol.style.Circle({
  14. radius: 7,
  15. fill: new ol.style.Fill({
  16. color: '#ffaa33'
  17. })
  18. })
  19. })
  20. });
  21.  
  22. map = new ol.Map({
  23. controls: ol.control.defaults({
  24. attribution: false
  25. }),
  26. target: 'map',
  27. layers: [
  28. new ol.layer.Tile({
  29. source: new ol.source.OSM()
  30. }),
  31. vector
  32. ],
  33. view: new ol.View({
  34. projection: 'EPSG:3857',
  35. center: ol.proj.transform([121, 37], 'EPSG:4326', 'EPSG:3857'),
  36. //center: [121, 37],
  37. zoom: 6
  38. })
  39. });
  40.  
  41. DrawPoint();

2、画点的方法

  1. function DrawPoint() {
  2. for (var i = 0; i < dataPie.length; i++) {
  3. var d = dataPie[i];
  4. var pt = ol.proj.transform([d.x, d.y], 'EPSG:4326', 'EPSG:3857');
  5.  
  6. var point = new ol.geom.Point(pt);
  7.  
  8. var feature = new ol.Feature(point);
  9.  
  10. sourceMeasure.addFeature(feature);
  11. }
  12. }

3、添加统计图

下面是原始的方法,可以显示统计图,但是初始位置不对,但是稍微拖动下地图,位置又跳到对的位置了,没找到问题,换成了后面的方法2

  1. //方法1
    //$("#addPieChart").on("click", function () {
  2. // clearChartOverlay();
  3. // for (var i = 0; i < dataPie.length; i++) {
  4. // var d = dataPie[i];
  5. // var pt = ol.proj.transform([d.x, d.y], 'EPSG:4326', 'EPSG:3857');
  6. // var domid = "chart" + guid();
  7. // $("#chart").append("<div id='" + domid + "'></div>");
  8. // var chart = new ol.Overlay({
  9. // id: domid,
  10. // position: pt,
  11. // positioning: "bottom-center",
  12. // element: document.getElementById(domid),
  13. // offset: [0, 18],
  14. // stopEvent: false //overlay也支持滚珠放大缩小
  15. // });
  16. // map.addOverlay(chart);
  17. // addPieChart(domid, d, 100);
  18. // overlayId.push(domid);
  19. // }
  20. //});

可能是因为对Overlay的element做了设置解决的这个问题,比较玄学

  1. //方法2
    $("#addPieChart").on("click", function () {
  2. clearChartOverlay();
  3. for (var i = 0; i < dataPie.length; i++) {
  4. var d = dataPie[i];
  5. var pt = ol.proj.transform([d.x, d.y], 'EPSG:4326', 'EPSG:3857');
  6. var domid = "chart" + guid();
  7. $("#chart").append("<div id='" + domid + "'></div>");
  8.  
  9. addPieChart(domid, d, 100);
  10.  
  11. var chart = new ol.Overlay({
  12. id: domid,
  13. element: document.getElementById(domid),
  14. positioning: "bottom-center", //统计图和渲染点位的位置关系
  15. offset: [0, 18],//如果统计图相对于点位又偏移,可以通过此属性将统计图移回来
  16. stopEvent: false //overlay也支持滚珠放大缩小
  17. });
  18. map.addOverlay(chart);
  19. var element = chart.getElement();
  20. chart.setPosition(pt);
  21. //使用下面的方法显示Overlay,可避免初始位置不对,拖动一下地图跳动的问题
  22. $(element).popover({
  23. placement: 'top',
  24. animation: false
  25. });
  26. $(element).popover('show');
  27. overlayId.push(domid);
  28. }
  29. });

  移除所有用来显示统计图的Overlay,和饼图的方法,highcharts里很多,想要别的风格可以去看highcharts的api

  1. /**
  2. * 移除统计图所使用的Overlay
  3. * */
  4. function clearChartOverlay() {
  5. for (var i = 0; i < overlayId.length; i++) {
  6. map.removeOverlay(map.getOverlayById(overlayId[i]));
  7. }
  8. }
  9.  
  10. function addPieChart(domid, data, size) {
  11. $('#' + domid).highcharts({
  12. chart: {
  13. backgroundColor: 'rgba(255, 255, 255, 0)',
  14. plotBorderColor: null,
  15. plotBackgroundColor: null,
  16. plotBackgroundImage: null,
  17. plotBorderWidth: null,
  18. plotShadow: false,
  19. width: size,
  20. height: size
  21. },
  22. tooltip: {
  23. pointFormat: '<b>{point.percentage:.1f}%</b>'
  24. },
  25. credits: {
  26. enabled: false
  27. },
  28. title: {
  29. text: ''
  30. },
  31. plotOptions: {
  32. pie: {
  33. dataLabels: {
  34. enabled: false
  35. }
  36. }
  37. },
  38. series: [{
  39. type: 'pie',
  40. name: data.name,
  41. data: data.data
  42. }]
  43. });
  44. }

  4、差不多就这么多,线状图和柱状图都类似,下面是完成代码

html

  1. @{
  2. ViewBag.Title = "StatisticalChart";
  3. Layout = "~/Views/Shared/_Layout.cshtml";
  4. }
  5.  
  6. @Styles.Render("~/Content/openlayers")
  7.  
  8. <div id="map" class="map">
  9.  
  10. </div>
  11. <div class="tool">
  12. <button id="addPieChart">添加饼图</button>
  13. <button id="addLineChart">添加线状图</button>
  14. <button id="addColumnChart">添加柱状图</button>
  15. </div>
  16. <div style="display: none;" id="chart">
  17. </div>
  18.  
  19. @Scripts.Render("~/bundles/openlayers")
  20. <script src="~/Scripts/openlayers/MapStatisticalChart.js"></script>
  21. <script src="~/Scripts/Highcharts/highcharts.js"></script>
  22. <script type="text/javascript">
  23.  
  24. $(document).ready(function () {
  25. init();
  26. });
  27.  
  28. </script>

  js

  1. /*
  2. *地图上显示统计图
  3. */
  4.  
  5. //地图渲染的两个对象
  6. var vector;
  7. var sourceMeasure;
  8.  
  9. //x,y表示渲染的位置,如果是点图层好说,如果是面或者线,需要获取中心点
  10. var overlayId = [];
  11. var dataPie = [{
  12. name: "乌鲁木齐", x: 87.5758285931, y: 43.7822116460, data: [
  13. {
  14. name: '男',
  15. y: 40.0,
  16. color: "#5ab1ef"
  17. }, {
  18. name: '女',
  19. y: 60.0,
  20. color: "#d87a80"
  21. }
  22. ]
  23. },
  24. {
  25. name: "拉萨", x: 91.1629975040, y: 29.7104204643, data: [
  26. {
  27. name: '男',
  28. y: 45.0,
  29. color: "#5ab1ef"
  30. }, {
  31. name: '女',
  32. y: 55.0,
  33. color: "#d87a80"
  34. }
  35. ]
  36. },
  37. {
  38. name: "北京", x: 116.4575803581078, y: 40.04054437977018, data: [
  39. {
  40. name: '男',
  41. y: 35.0,
  42. color: "#5ab1ef"
  43. }, {
  44. name: '女',
  45. y: 65.0,
  46. color: "#d87a80"
  47. }
  48. ]
  49. },
  50. {
  51. name: "兰州", x: 103.584297498, y: 36.1190864503, data: [
  52. {
  53. name: '男',
  54. y: 44.0,
  55. color: "#5ab1ef"
  56. }, {
  57. name: '女',
  58. y: 56.0,
  59. color: "#d87a80"
  60. }
  61. ]
  62. }];
  63. var map;
  64. function init() {
  65. sourceMeasure = new ol.source.Vector({ wrapX: false });
  66.  
  67. vector = new ol.layer.Vector({
  68. source: sourceMeasure,
  69. style: new ol.style.Style({
  70. fill: new ol.style.Fill({
  71. color: 'rgba(255, 255, 0, 0.2)'
  72. }),
  73. stroke: new ol.style.Stroke({
  74. color: '#ffcc33',
  75. width: 2
  76. }),
  77. image: new ol.style.Circle({
  78. radius: 7,
  79. fill: new ol.style.Fill({
  80. color: '#ffaa33'
  81. })
  82. })
  83. })
  84. });
  85.  
  86. map = new ol.Map({
  87. controls: ol.control.defaults({
  88. attribution: false
  89. }),
  90. target: 'map',
  91. layers: [
  92. new ol.layer.Tile({
  93. source: new ol.source.OSM()
  94. }),
  95. vector
  96. ],
  97. view: new ol.View({
  98. projection: 'EPSG:3857',
  99. center: ol.proj.transform([121, 37], 'EPSG:4326', 'EPSG:3857'),
  100. //center: [121, 37],
  101. zoom: 6
  102. })
  103. });
  104.  
  105. DrawPoint();
  106.  
  107. $("#addPieChart").on("click", function () {
  108. clearChartOverlay();
  109. for (var i = 0; i < dataPie.length; i++) {
  110. var d = dataPie[i];
  111. var pt = ol.proj.transform([d.x, d.y], 'EPSG:4326', 'EPSG:3857');
  112. var domid = "chart" + guid();
  113. $("#chart").append("<div id='" + domid + "'></div>");
  114.  
  115. addPieChart(domid, d, 100);
  116.  
  117. var chart = new ol.Overlay({
  118. id: domid,
  119. element: document.getElementById(domid),
  120. positioning: "bottom-center",
  121. offset: [0, 18],
  122. stopEvent: false //overlay也支持滚珠放大缩小
  123. });
  124. map.addOverlay(chart);
  125. var element = chart.getElement();
  126. chart.setPosition(pt);
  127. //使用下面的方法显示Overlay,可避免初始位置不对,拖动一下地图跳动的问题
  128. $(element).popover({
  129. placement: 'top',
  130. animation: false
  131. });
  132. $(element).popover('show');
  133. overlayId.push(domid);
  134. }
  135. });
  136.  
  137. $("#addLineChart").on("click", function () {
  138. clearChartOverlay();
  139. for (var i = 0; i < dataLine.length; i++) {
  140. var d = dataLine[i];
  141. var pt = ol.proj.transform([d.x, d.y], 'EPSG:4326', 'EPSG:3857');
  142. var domid = "chart" + guid();
  143. //$("#chart").append("<div id='" + domid + "'></div>");
  144. //var chart = new ol.Overlay({
  145. // id: domid,
  146. // position: pt,
  147. // positioning: "bottom-center",
  148. // element: document.getElementById(domid),
  149. // stopEvent: false //overlay也支持滚珠放大缩小
  150. //});
  151. //map.addOverlay(chart);
  152. //addLineChart(domid, d.data, 200, 150);
  153. //overlayId.push(domid);
  154.  
  155. $("#chart").append("<div id='" + domid + "'></div>");
  156. var chart = new ol.Overlay({
  157. id: domid,
  158. positioning: "bottom-center",
  159. element: document.getElementById(domid),
  160. stopEvent: false //overlay也支持滚珠放大缩小
  161. });
  162. map.addOverlay(chart);
  163. addLineChart(domid, d.data, 200, 150);
  164.  
  165. var element = chart.getElement();
  166. chart.setPosition(pt);
  167. //使用下面的方法显示Overlay,可避免初始位置不对,拖动一下地图跳动的问题
  168. $(element).popover({
  169. placement: 'top',
  170. animation: false
  171. });
  172. $(element).popover('show');
  173.  
  174. overlayId.push(domid);
  175. }
  176. });
  177.  
  178. $("#addColumnChart").on("click", function () {
  179. clearChartOverlay();
  180. for (var i = 0; i < dataColumn.length; i++) {
  181. var d = dataColumn[i];
  182. var pt = ol.proj.transform([d.x, d.y], 'EPSG:4326', 'EPSG:3857');
  183. var domid = "chart" + guid();
  184. $("#chart").append("<div id='" + domid + "'></div>");
  185. var chart = new ol.Overlay({
  186. id: domid,
  187. positioning: "bottom-center",
  188. element: document.getElementById(domid),
  189. offset: [0, 5],
  190. stopEvent: false //overlay也支持滚珠放大缩小
  191. });
  192. map.addOverlay(chart);
  193. addColumnChart(domid, d.data, 80, 80);
  194.  
  195. var element = chart.getElement();
  196. chart.setPosition(pt);
  197. //使用下面的方法显示Overlay,可避免初始位置不对,拖动一下地图跳动的问题
  198. $(element).popover({
  199. placement: 'top',
  200. animation: false
  201. });
  202. $(element).popover('show');
  203. overlayId.push(domid);
  204. }
  205. });
  206. }
  207. /**
  208. * 移除统计图所使用的Overlay
  209. * */
  210. function clearChartOverlay() {
  211. for (var i = 0; i < overlayId.length; i++) {
  212. map.removeOverlay(map.getOverlayById(overlayId[i]));
  213. }
  214. }
  215.  
  216. function addPieChart(domid, data, size) {
  217. $('#' + domid).highcharts({
  218. chart: {
  219. backgroundColor: 'rgba(255, 255, 255, 0)',
  220. plotBorderColor: null,
  221. plotBackgroundColor: null,
  222. plotBackgroundImage: null,
  223. plotBorderWidth: null,
  224. plotShadow: false,
  225. width: size,
  226. height: size
  227. },
  228. tooltip: {
  229. pointFormat: '<b>{point.percentage:.1f}%</b>'
  230. },
  231. credits: {
  232. enabled: false
  233. },
  234. title: {
  235. text: ''
  236. },
  237. plotOptions: {
  238. pie: {
  239. dataLabels: {
  240. enabled: false
  241. }
  242. }
  243. },
  244. series: [{
  245. type: 'pie',
  246. name: data.name,
  247. data: data.data
  248. }]
  249. });
  250. }
  251.  
  252. var dataLine = [{
  253. name: "乌鲁木齐", x: 87.5758285931, y: 43.7822116460, data: [
  254. {
  255. name: '安装,实施人员',
  256. series: [
  257. { x: 2010, y: 1234 },
  258. { x: 2011, y: 1234 }
  259. ],
  260. color: "#5ab1ef"
  261. }, {
  262. name: '工人',
  263. series: [
  264. { x: 2010, y: 245 },
  265. { x: 2011, y: 3454 }
  266. ],
  267. color: "#d87a80"
  268. }
  269. ]
  270. },
  271. {
  272. name: "拉萨", x: 91.1629975040, y: 29.7104204643, data: [
  273. {
  274. name: '安装,实施人员',
  275. series: [
  276. { x: 2010, y: 1234 },
  277. { x: 2011, y: 124 },
  278. { x: 2012, y: 0 }
  279. ],
  280. color: "#5ab1ef"
  281. }, {
  282. name: '工人',
  283. series: [
  284. { x: 2010, y: 245 },
  285. { x: 2011, y: 0 },
  286. { x: 2012, y: 3454 }
  287. ],
  288. color: "#d87a80"
  289. }
  290. ]
  291. }];
  292.  
  293. function addLineChart(domid, data, width, height) {
  294.  
  295. var categoriesX = [];
  296. var seriesValue = [];
  297. for (var i = 0; i < data.length; i++) {
  298. var value = [];
  299. for (var j = 0; j < data[i].series.length; j++) {
  300. categoriesX.push(data[i].series[j].x);
  301. value.push(data[i].series[j].y);
  302. }
  303.  
  304. seriesValue.push({ "name": data[i].name, "data": value });
  305. }
  306.  
  307. $('#' + domid).highcharts({
  308. chart: {
  309. backgroundColor: 'rgba(255, 255, 255, 0.8)',
  310. borderRadius: 20,
  311. plotBorderColor: null,
  312. plotBackgroundColor: null,
  313. plotBackgroundImage: null,
  314. plotBorderWidth: null,
  315. plotShadow: false,
  316. width: width,
  317. height: height
  318. },
  319. credits: {
  320. enabled: false
  321. },
  322. title: {
  323. text: ''
  324. },
  325. yAxis: {
  326. visible: false,
  327. title: {
  328. text: ''
  329. }
  330. },
  331. xAxis: {
  332. categories: categoriesX,
  333. crosshair: true
  334. },
  335. legend: {
  336. enabled: false
  337. },
  338. plotOptions: {
  339. series: {
  340. label: {
  341. connectorAllowed: false
  342. }
  343. },
  344. line: {
  345. dataLabels: {
  346. enabled: true,
  347. formatter: function () {
  348. return '<b>' + this.point.y + '</b><br>';
  349. }
  350. }
  351. }
  352. },
  353. series: seriesValue,
  354. responsive: {
  355. rules: [{
  356. condition: {
  357. maxWidth: 500
  358. },
  359. chartOptions: {
  360. legend: {
  361. layout: 'horizontal',
  362. align: 'center',
  363. verticalAlign: 'bottom'
  364. }
  365. }
  366. }]
  367. }
  368. });
  369. }
  370.  
  371. var dataColumn = [{
  372. name: "乌鲁木齐", x: 87.5758285931, y: 43.7822116460, data: [
  373. {
  374. name: '安装,实施人员',
  375. series: [
  376. { x: 2011, y: 1234 }
  377. ],
  378. color: "#5ab1ef"
  379. }, {
  380. name: '工人',
  381. series: [
  382. { x: 2011, y: 3454 }
  383. ],
  384. color: "#d87a80"
  385. }
  386. ]
  387. },
  388. {
  389. name: "拉萨", x: 91.1629975040, y: 29.7104204643, data: [
  390. {
  391. name: '安装,实施人员',
  392. series: [
  393. { x: 2012, y: 123 }
  394. ],
  395. color: "#5ab1ef"
  396. }, {
  397. name: '工人',
  398. series: [
  399. { x: 2012, y: 3454 }
  400. ],
  401. color: "#d87a80"
  402. }
  403. ]
  404. }, {
  405. name: "北京", x: 116.4575803581078, y: 40.04054437977018, data: [
  406. {
  407. name: '安装,实施人员',
  408. series: [
  409. { x: 2014, y: 252 }
  410. ],
  411. color: "#5ab1ef"
  412. }, {
  413. name: '工人',
  414. series: [
  415. { x: 2014, y: 324 }
  416. ],
  417. color: "#d87a80"
  418. }
  419. ]
  420. },
  421. {
  422. name: "兰州", x: 103.584297498, y: 36.1190864503, data: [
  423. {
  424. name: '安装,实施人员',
  425. series: [
  426. { x: 2013, y: 2341 }
  427. ],
  428. color: "#5ab1ef"
  429. }, {
  430. name: '工人',
  431. series: [
  432. { x: 2013, y: 2341 }
  433. ],
  434. color: "#d87a80"
  435. }
  436. ]
  437. }];
  438.  
  439. function addColumnChart(domid, data, width, height) {
  440.  
  441. var categoriesX = [];
  442. var seriesValue = [];
  443. for (var i = 0; i < data.length; i++) {
  444. var value = [];
  445. for (var j = 0; j < data[i].series.length; j++) {
  446. categoriesX.push(data[i].series[j].x);
  447. value.push(data[i].series[j].y);
  448. }
  449.  
  450. seriesValue.push({ "name": data[i].name, "data": value });
  451. }
  452.  
  453. $('#' + domid).highcharts({
  454. chart: {
  455. backgroundColor: 'rgba(255, 255, 255, 0)',
  456. borderRadius: 20,
  457. plotBorderColor: null,
  458. plotBackgroundColor: null,
  459. plotBackgroundImage: null,
  460. plotBorderWidth: null,
  461. plotShadow: false,
  462. width: width,
  463. height: height,
  464. type: 'column'
  465. },
  466. credits: {
  467. enabled: false
  468. },
  469. title: {
  470. text: ''
  471. },
  472. yAxis: {
  473. visible: false,
  474. title: {
  475. text: ''
  476. }
  477. },
  478. xAxis: {
  479. visible: false,
  480. categories: categoriesX,
  481. crosshair: true
  482. },
  483. legend: {
  484. enabled: false
  485. },
  486. plotOptions: {
  487. series: {
  488. label: {
  489. connectorAllowed: false
  490. }
  491. },
  492. line: {
  493. dataLabels: {
  494. enabled: true,
  495. formatter: function () {
  496. return '<b>' + this.point.y + '</b><br>';
  497. }
  498. }
  499. }
  500. },
  501. series: seriesValue,
  502. responsive: {
  503. rules: [{
  504. condition: {
  505. maxWidth: 500
  506. },
  507. chartOptions: {
  508. legend: {
  509. layout: 'horizontal',
  510. align: 'center',
  511. verticalAlign: 'bottom'
  512. }
  513. }
  514. }]
  515. }
  516. });
  517. }
  518.  
  519. function DrawPoint() {
  520. for (var i = 0; i < dataPie.length; i++) {
  521. var d = dataPie[i];
  522. var pt = ol.proj.transform([d.x, d.y], 'EPSG:4326', 'EPSG:3857');
  523.  
  524. var point = new ol.geom.Point(pt);
  525.  
  526. var feature = new ol.Feature(point);
  527.  
  528. sourceMeasure.addFeature(feature);
  529. }
  530. }

  引用的资料包括:https://blog.csdn.net/gisshixisheng/article/details/50926948,https://blog.csdn.net/henrystern/article/details/81149015

 友情链接:直通硅谷  点职佳  北美留学生论坛

本站QQ群:前端 618073944 | Java 606181507 | Python 626812652 | C/C++ 612253063 | 微信 634508462 | 苹果 692586424 | C#/.net 182808419 | PHP 305140648 | 运维 608723728

W3xue 的所有内容仅供测试,对任何法律问题及风险不承担任何责任。通过使用本站内容随之而来的风险与本站无关。
关于我们  |  意见建议  |  捐助我们  |  报错有奖  |  广告合作、友情链接(目前9元/月)请联系QQ:27243702 沸活量
皖ICP备17017327号-2 皖公网安备34020702000426号