Map.js 34 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277
  1. import OLMap from 'ol/Map'
  2. import View from 'ol/View'
  3. import * as proj from 'ol/proj'
  4. import * as interaction from 'ol/interaction'
  5. import {Draw,Modify} from 'ol/interaction'
  6. import 'ol/ol.css'
  7. import './css/KMap.css'
  8. import * as Enum from './Enum'
  9. import Common from './Common'
  10. import VectorLayer from './VectorLayer'
  11. import * as Extent from 'ol/extent'
  12. import Overlay from 'ol/Overlay'
  13. import WMTSLayer from './WMTSLayer'
  14. import XYZLayer from './XYZLayer'
  15. import config from "@/api/config.js";
  16. import {Feature} from "ol";
  17. import {GeoJSON, WKT} from 'ol/format'
  18. import { Style, Text } from 'ol/style';
  19. import { Circle, Fill, Stroke } from 'ol/style.js';
  20. import { LineString, Point } from 'ol/geom';
  21. import {getArea} from "ol/sphere"
  22. /**
  23. * @description KMap.Map 地图类
  24. */
  25. class Map {
  26. /**
  27. * @description 地图实例
  28. * @static
  29. * @memberof Map
  30. */
  31. Instance = null
  32. /**
  33. * @description 信息窗体像素对象
  34. * @memberof Map
  35. */
  36. infoWindowPixel = null
  37. /**
  38. * @description 鼠标移动事件弹窗UID
  39. * @memberof Map
  40. */
  41. InfowindowmoveUID = -1
  42. /**
  43. * @description 鼠标点击事件弹窗UID
  44. * @memberof Map
  45. */
  46. InfowindowclickUID = -1
  47. /**
  48. * @description 是否有鼠标移动弹窗
  49. * @memberof Map
  50. */
  51. ClearMouseMoveInfoWindow = false
  52. /**
  53. * @description X方向缩放
  54. * @memberof Map
  55. */
  56. scaleX = 1
  57. /**
  58. * @description Y方向缩放
  59. * @memberof Map
  60. */
  61. scaleY = 1
  62. /**
  63. * @param {string} id DOM元素ID
  64. * @param {number} zoomLevel 地图层级
  65. * @param {number} lng 纬度
  66. * @param {number} lat 经度
  67. * @description Map初始化方法
  68. * @constructor
  69. */
  70. constructor(id,zoomLevel,lng,lat,projection, minZoom,maxZoom){
  71. if(Map.Instance){
  72. Map.Instance = false;
  73. }
  74. if(projection){
  75. projection = proj.get(projection)
  76. }
  77. projection = projection || proj.get("EPSG:4326");
  78. const vm = this
  79. Map.Instance = this
  80. let lnglat = [lng,lat]
  81. if(projection.getCode() == "EPSG:3857"){
  82. lnglat = proj.fromLonLat(lnglat);
  83. }
  84. Common.checkLngLat(lng,lat)
  85. let view = new View({
  86. center: lnglat,
  87. zoom: zoomLevel,
  88. minZoom: minZoom || Common.ShowLevel[0],
  89. maxZoom: maxZoom || Common.ShowLevel[1],
  90. projection:projection
  91. })
  92. this.view = view
  93. this.map = new OLMap({
  94. interactions: interaction.defaults().extend([
  95. new interaction.DragRotateAndZoom()]),
  96. target: id,
  97. layers: [],//vm.baseLayer
  98. view: view,
  99. control: []
  100. })
  101. this.initBaseLayer(projection)
  102. //初始化业务图层
  103. this.initBusinessLayer()
  104. //初始化地图信息弹窗
  105. this.initInfoWindow()
  106. //初始化地图基础事件
  107. this.initMapBaseEvent()
  108. }
  109. /**
  110. * 初始化地图底图图层
  111. * @return {array}
  112. * @memberof Map
  113. */
  114. async initBaseLayer(projection){
  115. const img_wmts = await VE_API.system.getCfg({"k":"img_wmts_mkt","resultType":"json"});
  116. const cva_wmts = await VE_API.system.getCfg({"k":"cva_wmts_mkt","resultType":"json"});
  117. this.tdtImgLayer = new WMTSLayer(img_wmts.data, projection,this);
  118. this.cva_torLayer = new WMTSLayer(cva_wmts.data,projection,this);
  119. let xyz2 = config.base_img_url3 + 'map/lby/{z}/{x}/{y}.png';
  120. this.addXYZLayer(xyz2,{minZoom:15,maxZoom:22});
  121. }
  122. addXYZLayer(url,options){
  123. let xyz = new XYZLayer(url,options,3);
  124. return xyz;
  125. }
  126. /**
  127. * @description 初始化业务图层
  128. * @memberof Map
  129. */
  130. initBusinessLayer(){
  131. const vm = this
  132. let map = vm.map
  133. //创建默认点标记图层
  134. vm.markerLayer = new VectorLayer("defaultMarkerLayer",101)
  135. //创建默认线标记图层
  136. vm.polyLineLayer = new VectorLayer("defaultPolylineLayer",101)
  137. //创建默认面图层
  138. vm.polygonLayer = new VectorLayer("defaultPolygonLayer",1000)
  139. //创建文本标记图层
  140. vm.labelLayer = new VectorLayer("defaultLabelLayer",99)
  141. map.addLayer(vm.polygonLayer.layer)
  142. map.once('postrender', function(event) {
  143. map.addLayer(vm.markerLayer.layer)
  144. map.addLayer(vm.polyLineLayer.layer)
  145. map.addLayer(vm.labelLayer.layer)
  146. map.on('click',function(evt){
  147. let coordinate = evt.coordinate;
  148. // let newPoints = proj.transform(coordinate, 'EPSG:3857', 'EPSG:4326');
  149. // debugger;
  150. })
  151. // map.addLayer(layer)
  152. })
  153. }
  154. initDraw(callback){
  155. const vm = this
  156. this.draw = new Draw({
  157. type: 'MultiPolygon',
  158. source: this.polygonLayer.source,
  159. free: true,
  160. style: vm.drawStyleFunc
  161. })
  162. this.draw.setActive(false)
  163. this.map.addInteraction(this.draw);
  164. this.draw.on("drawend",callback)
  165. }
  166. startDraw(){
  167. this.draw.setActive(true)
  168. }
  169. endDraw(){
  170. this.draw.setActive(false)
  171. }
  172. modifyDraw(callback) {
  173. this.modify = new Modify({
  174. source: this.polygonLayer.source,
  175. pixelTolerance: 10, //设置吸附像素值
  176. })
  177. this.map.addInteraction(this.modify);
  178. this.modify.on("modifyend",callback)
  179. }
  180. drawStyleFunc(feature) {
  181. const styles = [];
  182. const type = feature.getGeometry().getType();
  183. const coord = feature.getGeometry().getCoordinates();
  184. for (let i = 0; i < coord.length - 1; i++) {
  185. if (i%2) {
  186. styles.push(
  187. new Style({
  188. geometry: new Point(coord[i]),
  189. image: new Circle({
  190. radius: 6,
  191. fill: new Fill({
  192. color: '#06F7A1'
  193. }),
  194. stroke: new Stroke({
  195. color: '#fff',
  196. width: 1
  197. })
  198. })
  199. })
  200. );
  201. } else {
  202. styles.push(
  203. new Style({
  204. geometry: new Point(coord[i]),
  205. image: new Circle({
  206. radius: 6,
  207. fill: new Fill({
  208. color: '#fff'
  209. }),
  210. })
  211. })
  212. );
  213. }
  214. }
  215. if (type === 'LineString') {
  216. for (let i = 0; i < coord.length - 1; i++) {
  217. styles.push(
  218. new Style({
  219. geometry: new LineString([coord[i], coord[i + 1]]),
  220. stroke: new Stroke({
  221. color: '#06F7A1',
  222. width: 2
  223. })
  224. })
  225. );
  226. }
  227. }
  228. return styles;
  229. }
  230. polygonStyle(feature) {
  231. const styles = [];
  232. const coord = feature.getGeometry().getCoordinates()[0];
  233. for (let i = 0; i < coord[0].length - 1; i++) {
  234. if (i%2) {
  235. styles.push(
  236. new Style({
  237. geometry: new Point(coord[0][i]),
  238. image: new Circle({
  239. radius: 4,
  240. fill: new Fill({
  241. color: '#54cb82'
  242. }),
  243. stroke: new Stroke({
  244. color: '#54cb82',
  245. width: 3
  246. })
  247. })
  248. })
  249. );
  250. } else {
  251. styles.push(
  252. new Style({
  253. geometry: new Point(coord[0][i]),
  254. image: new Circle({
  255. radius: 6,
  256. fill: new Fill({
  257. color: '#fff'
  258. })
  259. })
  260. })
  261. );
  262. }
  263. }
  264. let fillStyle = new Style({
  265. fill: new Fill({
  266. color: [1, 41, 52, 0.6]
  267. }),
  268. stroke: new Stroke({
  269. color: '#54cb82',
  270. width: 2
  271. })
  272. })
  273. let geom = feature.getGeometry().clone()
  274. geom.transform(proj.get("EPSG:4326"), proj.get("EPSG:38572"))
  275. let area = getArea(geom)
  276. area = (area + area / 2) / 1000;
  277. let areaValStyle = new Style({
  278. text: new Text({
  279. font: "16px sans-serif",
  280. text: area.toFixed(2) + "亩",
  281. // offsetX: 28,
  282. // offsetY: -100,
  283. fill: new Fill({ color: "#fff" }), // 字体颜色
  284. }),
  285. })
  286. styles.push(fillStyle, areaValStyle);
  287. return styles;
  288. }
  289. getLayerFeatures() {
  290. const vm = this
  291. let features = vm.polygonLayer.source.getFeatures()
  292. return features
  293. }
  294. // 传入geojson,回显到polygon
  295. setLayerPolygon(geometry) {
  296. const vm = this
  297. vm.polygonLayer.source.addFeatures(new GeoJSON().readFeatures(geometry))
  298. }
  299. setLayerWkt(wkt,isView) {
  300. const vm = this
  301. let f = new Feature({geometry:new WKT().readGeometry(wkt)})
  302. const extent = f.getGeometry().getExtent()
  303. vm.polygonLayer.source.addFeature(f)
  304. if(isView){
  305. vm.map.getView().fit(extent, { padding: [20, 20, 20, 20] });
  306. }
  307. }
  308. addLayer(layer){
  309. const vm = this
  310. vm.map.addLayer(layer)
  311. }
  312. removeLayer(layer){
  313. const vm = this
  314. vm.map.removeLayer(layer)
  315. }
  316. /**
  317. * @description 初始化信息弹窗
  318. * @memberof Map
  319. */
  320. initInfoWindow(){
  321. const vm = this
  322. //创建地图弹窗容器
  323. let infoWindowBoxClick = document.createElement("div")
  324. let infoWindowBoxMove = document.createElement("div")
  325. let mapTarget = vm.map.getTargetElement()
  326. infoWindowBoxClick.id = "infowindow-click"
  327. infoWindowBoxMove.id = "infowindow-move"
  328. infoWindowBoxClick.style.zIndex = 999
  329. infoWindowBoxMove.style.zIndex = 999
  330. mapTarget.appendChild(infoWindowBoxClick)
  331. mapTarget.appendChild(infoWindowBoxMove)
  332. vm.infoWindow_click = new Overlay({
  333. element: infoWindowBoxClick
  334. })
  335. vm.infoWindow_move = new Overlay({
  336. element: infoWindowBoxMove
  337. })
  338. //添加点击弹窗
  339. vm.map.addOverlay(vm.infoWindow_click)
  340. //添加悬停弹窗
  341. vm.map.addOverlay(vm.infoWindow_move)
  342. }
  343. /**
  344. * @description 初始化地图基础事件
  345. * @memberof Map
  346. */
  347. initMapBaseEvent(){
  348. const vm = this
  349. var allowTriggerEvent = function(pixel) {
  350. var infoWindowPixel = vm.infoWindowPixel
  351. if(infoWindowPixel == null){
  352. return true
  353. }
  354. var x = pixel[0]
  355. var y = pixel[1]
  356. if(x>=infoWindowPixel[0] && x<=infoWindowPixel[2] &&
  357. y>=infoWindowPixel[1] && y<=infoWindowPixel[3]) {
  358. return false
  359. }
  360. return true
  361. }
  362. vm.map.on('click',function(event){
  363. event.pixel[0] = (event.pixel[0] / vm.scaleX)
  364. event.pixel[1] = (event.pixel[1] / vm.scaleY)
  365. var clickFeature = vm.map.forEachFeatureAtPixel(event.pixel, function(feature){
  366. if(!allowTriggerEvent(event.pixel)) return
  367. // 为点击到的feature发送自定义的click消息
  368. if(feature.dispatchEvent != undefined){
  369. feature.dispatchEvent({type: 'click', event: event})
  370. }
  371. return feature
  372. })
  373. //点击在地图空白处时清空弹窗
  374. if(clickFeature == undefined){
  375. vm.clearInfoWindow()
  376. }
  377. })
  378. //为地图注册鼠标点击事件的监听
  379. vm.map.on('pointermove', function(event) {
  380. event.pixel[0] = (event.pixel[0] / vm.scaleX)
  381. event.pixel[1] = (event.pixel[1] / vm.scaleY)
  382. var mousemoveFeature = vm.map.forEachFeatureAtPixel(event.pixel, function(feature){
  383. if(!allowTriggerEvent(event.pixel)){
  384. return
  385. }
  386. // 为点击到的feature发送自定义的mousemove消息
  387. if(feature.dispatchEvent != undefined){
  388. feature.dispatchEvent({type: 'mousemove', event: event})
  389. }
  390. return feature
  391. })
  392. //悬停在地图空白处时清空悬停弹窗
  393. if(mousemoveFeature == undefined)
  394. {
  395. vm.clearMouseMoveInfoWindow()
  396. }
  397. //设置鼠标悬停到覆盖物上的样式
  398. var mapContainer = vm.getTarget()
  399. if(mousemoveFeature) {
  400. mapContainer.style.cursor = "pointer"
  401. }
  402. else {
  403. mapContainer.style.cursor = "default"
  404. }
  405. })
  406. }
  407. setScale(x, y) {
  408. const vm = this
  409. // var mapContainer = vm.getTarget()
  410. // mapContainer.style.overflow = 'hidden'
  411. // var mapContent = mapContainer.getElementsByClassName('ol-viewport')[0]
  412. // var scaleX = 1 / Number(x);
  413. // var scaleY = 1 / Number(y);
  414. vm.scaleX = Number(x)
  415. vm.scaleY = Number(y)
  416. // mapContent.style.transform = "scale("+scaleX+","+scaleY+")"
  417. }
  418. /**
  419. * @description 清除鼠标点击弹窗
  420. * @memberof Map
  421. */
  422. clearInfoWindow() {
  423. const vm = this
  424. vm.infoWindow_click.setPosition(undefined)
  425. vm.infoWindow_move.setPosition(undefined)
  426. vm.infoWindowPixel = null
  427. vm.InfowindowmoveUID = -1
  428. vm.InfowindowclickUID = -1
  429. }
  430. /**
  431. * @description 清除鼠标移动弹窗
  432. * @memberof Map
  433. */
  434. clearMouseMoveInfoWindow() {
  435. const vm = this
  436. if(vm.ClearMouseMoveInfoWindow) {
  437. vm.infoWindow_move.setPosition(undefined)
  438. vm.infoWindowPixel = null
  439. vm.InfowindowmoveUID = -1
  440. }
  441. }
  442. /**
  443. * @description 获取地图容器div
  444. * @returns 地图容器div
  445. * @memberof Map
  446. */
  447. getTarget() {
  448. let target = this.map.getTargetElement()
  449. return target
  450. }
  451. /**
  452. * @description 获取地图容器尺寸
  453. * @returns KMap.Size格式的尺寸
  454. * @memberof Map
  455. */
  456. getSize() {
  457. let size = this.map.getSize()
  458. console.log(Common)
  459. size = Common.MapSize2KMapSize(size)
  460. return size
  461. }
  462. /**
  463. * @description 获取地图投影EPSG类型
  464. * @returns 地图投影类型
  465. * @memberof Map
  466. */
  467. getProjection() {
  468. let projection = this.view.getProjection()
  469. return projection
  470. }
  471. /**
  472. * @description 获取地图中心
  473. * @returns 地图中心,KMap.LngLat对象格式
  474. * @memberof Map
  475. */
  476. getCenter() {
  477. let center = this.view.getCenter()
  478. center = proj.toLonLat(center)
  479. return Common.MapLngLat2KMapLngLat(center)
  480. }
  481. /**
  482. * @description 获取地图中心
  483. * @returns 地图中心,KMap.LngLat对象格式
  484. * @memberof Map
  485. */
  486. getCenter2() {
  487. let center = this.view.getCenter()
  488. center = proj.toLonLat(center)
  489. return center
  490. }
  491. /**
  492. * @description 设置地图中心
  493. * @param {KMap.LngLat} position 地图中心位置,KMap.LngLat对象格式,必填
  494. * @memberof Map
  495. */
  496. setCenter(position) {
  497. let centerlnglat = Common.KMapLngLat2MapLngLat(position)
  498. let center = proj.fromLonLat(centerlnglat)
  499. this.view.setCenter(center)
  500. }
  501. getView(){
  502. return this.view;
  503. }
  504. /**
  505. * @description 设置地图中心
  506. * @param {KMap.LngLat} position 地图中心位置,KMap.LngLat对象格式,必填
  507. * @memberof Map
  508. */
  509. setCenter2(position) {
  510. this.view.setCenter(position)
  511. }
  512. fitToView(center,zoom,dera) {
  513. this.view.fit(center,{duration: dera})
  514. }
  515. /**
  516. * @description 地图中心点平移至指定点位置
  517. * @param {KMap.LngLat} point 指定点经纬度坐标,KMap.LngLat对象格式,必填
  518. * @param {number} zoom 缩放级别,选填参数,不填则使用当前缩放级别
  519. * @memberof Map
  520. */
  521. panTo(point,zoom) {
  522. point = Common.KMapLngLat2MapLngLat(point)
  523. let center = proj.fromLonLat(point)
  524. if(zoom) {
  525. this.view.animate({center:center},{zoom:zoom})
  526. }
  527. else {
  528. this.view.animate({center:center})
  529. }
  530. }
  531. /**
  532. * @description 地图放大一级显示
  533. * @memberof Map
  534. */
  535. zoomIn() {
  536. this.view.setZoom( this.getZoom() + 1 )
  537. return this.getZoom()
  538. }
  539. /**
  540. * @description 地图缩小一级显示
  541. * @memberof Map
  542. */
  543. zoomOut() {
  544. this.view.setZoom( this.getZoom() - 1)
  545. return this.getZoom()
  546. }
  547. /**
  548. * @description 缩放到点标记图层范围
  549. * @param {number} duration 选填参数,动画时长(单位:毫秒),不填则使用默认的0毫秒
  550. * @memberof Map
  551. */
  552. zoomToMarkerLayer(duration) {
  553. const vm = this
  554. duration = (duration != undefined)? duration : 0
  555. let markers = vm.markerLayer.getSource().getFeatures()
  556. let coordinateArray = new Array()
  557. for(let i=0; i<markers.length; i++) {
  558. coordinateArray.push(markers[i].getGeometry().getCoordinates())
  559. }
  560. let extentBound = new Extent.boundingExtent(coordinateArray)
  561. this.view.fit(extentBound,{
  562. duration: duration
  563. })
  564. this.view.fit(vm.markerLayer.getSource().getExtent(),{
  565. duration: duration
  566. })
  567. }
  568. /**
  569. * @description 缩放到点标记集合范围
  570. * @param {Array} markerArray 点标记集合,必填
  571. * @param {number} duration 选填参数,动画时长(单位:毫秒),不填则使用默认的0毫秒
  572. * @memberof Map
  573. */
  574. zoomToMarkerArray(markerArray,duration) {
  575. duration = (duration != undefined)? duration : 0
  576. let coordinateArray = new Array()
  577. for(let i=0; i<markerArray.length; i++) {
  578. coordinateArray.push(markerArray[i].Marker.getGeometry().getCoordinates())
  579. }
  580. let extentBound = new Extent.boundingExtent(coordinateArray)
  581. this.view.fit(extentBound,{
  582. duration: duration
  583. })
  584. }
  585. /**
  586. * @description 缩放到文本标记图层范围
  587. * @param {number} duration 选填参数,动画时长(单位:毫秒),不填则使用默认的0毫秒
  588. * @memberof Map
  589. */
  590. zoomToLabelLayer(duration) {
  591. const vm = this;
  592. duration = (duration != undefined)? duration : 0
  593. this.view.fit(vm.labelLayer.getSource().getExtent(),{
  594. duration: duration
  595. })
  596. }
  597. /**
  598. * @description 缩放到文本标记集合范围
  599. * @param {Array} labelArray 文本标记集合,必填
  600. * @param {number} duration 选填参数,动画时长(单位:毫秒),不填则使用默认的0毫秒
  601. * @memberof Map
  602. */
  603. zoomToLabelArray(labelArray,duration) {
  604. duration = (duration != undefined)? duration : 0
  605. let coordinateArray = new Array()
  606. for(let i=0; i<labelArray.length; i++) {
  607. coordinateArray.push(labelArray[i].Label.getGeometry().getCoordinates())
  608. }
  609. let extentBound = new Extent.boundingExtent(coordinateArray)
  610. this.view.fit(extentBound,{
  611. duration: duration
  612. })
  613. }
  614. /**
  615. * @description 缩放到线图层范围
  616. * @param {number} duration 选填参数,动画时长(单位:毫秒),不填则使用默认的0毫秒
  617. * @memberof Map
  618. */
  619. zoomToPolylineLayer(duration) {
  620. const vm = this
  621. duration = (duration != undefined)? duration : 0
  622. this.view.fit(vm.polyLineLayer.getSource().getExtent(),{
  623. duration: duration
  624. })
  625. }
  626. /**
  627. * @description 缩放到线标记集合范围
  628. * @param {Array} lineArray 线标记集合,必填
  629. * @param {number} duration 选填参数,动画时长(单位:毫秒),不填则使用默认的0毫秒
  630. * @memberof Map
  631. */
  632. zoomToPolylineArray(lineArray,duration) {
  633. duration = (duration != undefined)? duration : 0
  634. let coordinateArray = new Array()
  635. for(let i=0; i<lineArray.length; i++) {
  636. let coordinates = lineArray[i].polyline.getGeometry().getCoordinates()
  637. for(let z=0; z<coordinates.length; z++) {
  638. coordinateArray.push(coordinates[z])
  639. }
  640. }
  641. let extentBound = new Extent.boundingExtent(coordinateArray)
  642. this.view.fit(extentBound,{
  643. duration: duration
  644. })
  645. }
  646. /**
  647. * @description 缩放到经纬度数组范围
  648. * @param {Array} lngLatArray KMap.LngLat格式的经纬度坐标数组,必填
  649. * @param {number} duration 选填参数,动画时长(单位:毫秒),不填则使用默认的0毫秒
  650. * @memberof Map
  651. */
  652. zoomToLngLatArray(lngLatArray,duration) {
  653. duration = (duration != undefined)? duration : 0
  654. let coordinateArray = new Array()
  655. for(let i=0; i<lngLatArray.length; i++) {
  656. let point = Common.KMapLngLat2MapLngLat(lngLatArray[i])
  657. coordinateArray.push(proj.fromLonLat(point))
  658. }
  659. let extentBound = new Extent.boundingExtent(coordinateArray)
  660. this.view.fit(extentBound,{
  661. duration: duration
  662. })
  663. }
  664. /**
  665. * @description 调整地图视角到能够显示所有覆盖物的合适矩形范围
  666. * @param {number} duration 选填参数,动画时长(单位:毫秒),不填则使用默认的0毫秒
  667. * @memberof Map
  668. */
  669. setFitView(duration) {
  670. const vm = this
  671. //获取所有元素坐标点集合
  672. let LonLatArray = new Array()
  673. let markers = vm.markerLayer.getSource().getFeatures()
  674. let labels = vm.labelLayer.getSource().getFeatures()
  675. let polylines = vm.polyLineLayer.getSource().getFeatures()
  676. let features = [markers,labels,polylines]
  677. for(let i=0; i<features.length; i++) {
  678. for(let z=0; z<features[i].length; z++) {
  679. let featureLonLats = features[i][z].getGeometry().getCoordinates()
  680. if(features[i] != polylines) {
  681. LonLatArray.push(featureLonLats)
  682. }
  683. else {
  684. for(let m=0; m<featureLonLats.length; m++) {
  685. LonLatArray.push(featureLonLats[m])
  686. }
  687. }
  688. }
  689. }
  690. //地图视角切换到坐标点集合的矩形范围
  691. duration = (duration != undefined)? duration : 0
  692. let extentBound = new Extent.boundingExtent(LonLatArray)
  693. this.view.fit(extentBound,{
  694. duration: duration
  695. })
  696. }
  697. /**
  698. * @description 获取地图分辨率
  699. * @returns {number} 地图分辨率
  700. * @memberof Map
  701. */
  702. getResolution() {
  703. let resolution = this.view.getResolution()
  704. return resolution
  705. }
  706. /**
  707. * @description 获取地图当前缩放值
  708. * @returns {number} 地图缩放级别
  709. * @memberof Map
  710. */
  711. getZoom() {
  712. let zoom = this.view.getZoom()
  713. return zoom
  714. }
  715. /**
  716. * @description 设置地图当前缩放值
  717. * @param {number}zoom 缩放值,必填
  718. * @memberof Map
  719. */
  720. setZoom(zoom) {
  721. this.view.setZoom(zoom)
  722. }
  723. /**
  724. * @description 获取地图最大缩放值
  725. * @returns {number} 最大缩放值
  726. * @memberof Map
  727. */
  728. getMaxZoom() {
  729. let maxZoom = this.view.getMaxZoom()
  730. return maxZoom
  731. }
  732. /**
  733. * @description 设置地图最大缩放值
  734. * @param {number} zoom 最大缩放值,必填
  735. * @memberof Map
  736. */
  737. setMaxZoom(zoom) {
  738. this.view.setMaxZoom(zoom)
  739. }
  740. /**
  741. * @description 获取地图最小缩放值
  742. * @returns {number} 最小缩放值
  743. * @memberof Map
  744. */
  745. getMinZoom () {
  746. let minZoom = this.view.getMinZoom()
  747. return minZoom
  748. }
  749. /**
  750. * @description 设置地图最小缩放值
  751. * @param {number} zoom 最小缩放值,必填
  752. * @memberof Map
  753. */
  754. setMinZoom(zoom) {
  755. this.view.setMinZoom(zoom)
  756. }
  757. /**
  758. * @description 设置地图中心和缩放级别
  759. * @param {number} zoom 缩放级别,必填
  760. * @param {KMap.LngLat} center 地图中心 KMap.LngLat对象格式,必填
  761. * @param {boolean} animate 选填,是否使用缓冲动画,默认为false
  762. * @memberof Map
  763. */
  764. setZoomAndCenter(zoom,center,animate) {
  765. let centerlnglat = Common.KMapLngLat2MapLngLat(center)
  766. center = proj.fromLonLat(centerlnglat)
  767. if(animate) {
  768. this.view.animate({center:center,zoom:zoom})
  769. }
  770. else {
  771. this.view.setCenter(center)
  772. this.view.setZoom(zoom)
  773. }
  774. }
  775. /**
  776. * @description 获取地图经纬度矩形范围
  777. * @returns {KMap.Bounds} 地图经纬度矩形范围,KMap.Bounds格式
  778. * @memberof Map
  779. */
  780. getBounds() {
  781. const vm = this;
  782. let bounds = vm.view.calculateExtent(vm.map.getSize())
  783. let southWest = proj.toLonLat([bounds[0],bounds[1]])
  784. let northEast = proj.toLonLat([bounds[2],bounds[3]])
  785. bounds = [southWest[0],southWest[1],northEast[0],northEast[1]]
  786. let mapBound = Common.MapBounds2KMapBounds(bounds)//将OL的Bounds格式转换成KMap的Bounds格式
  787. return mapBound
  788. }
  789. /**
  790. * @description 设置地图经纬度矩形范围
  791. * @param {KMap.Bounds} bound 地图经纬度矩形范围,KMap.Bounds格式,必填
  792. * @memberof Map
  793. */
  794. setBounds(bound) {
  795. let lnglatArray = new Array()
  796. let mapBound = Common.KMapBounds2MapBounds(bound)//将KMap的Bounds格式转换成OL的Bounds格式
  797. lnglatArray.push(proj.fromLonLat([mapBound[0],mapBound[1]]))
  798. lnglatArray.push(proj.fromLonLat([mapBound[2],mapBound[3]]))
  799. let bounds = new Extent.boundingExtent(lnglatArray)
  800. this.view.fit(bounds) //地图视角切换到矩阵范围
  801. }
  802. /**
  803. * @description 设置地图经纬度矩形范围
  804. * @param {[minLng,minLat,maxLng,maxLat]} bound 地图经纬度矩形范围,KMap.Bounds格式,必填
  805. * @memberof Map
  806. */
  807. fitBounds(bound) {
  808. let lnglatArray = new Array();
  809. lnglatArray.push(proj.fromLonLat([bound[0],bound[1]]))
  810. lnglatArray.push(proj.fromLonLat([bound[2],bound[3]]))
  811. let bounds = new Extent.boundingExtent(lnglatArray)
  812. this.view.fit(bounds) //地图视角切换到矩阵范围
  813. }
  814. fit(geometryOrExtent,options){
  815. this.view.fit(geometryOrExtent,{ duration:500})
  816. }
  817. /**
  818. * @description 平面地图像素坐标转经纬度坐标
  819. * @param {KMap.Pixel} pixel 平面地图像素坐标,格式为KMap.Pixel对象,必填
  820. * @returns {KMap.LngLat} 经纬度坐标,格式为KMap.LngLat对象
  821. * @memberof Map
  822. */
  823. pixelToLngLat(pixel) {
  824. pixel = Common.KMapPixel2MapPixel(pixel)
  825. let lnglat = new proj.toLonLat(pixel)
  826. return Common.MapLngLat2KMapLngLat(lnglat)
  827. }
  828. /**
  829. * @description 经纬度坐标转平面地图像素坐标
  830. * @param {KMap.LngLat} lnglat 经纬度坐标,格式为KMap.LngLat对象,必填
  831. * @returns {KMap.Pixel} 地图像素坐标,格式为KMap.Pixel对象
  832. * @memberof Map
  833. */
  834. lnglatToPixel(lnglat) {
  835. lnglat = Common.KMapLngLat2MapLngLat(lnglat)
  836. let pixel = proj.fromLonLat(lnglat)
  837. return Common.MapPixel2KMapPixel(pixel)
  838. }
  839. /**
  840. * @description 地图容器屏幕坐标转经纬度坐标
  841. * @param {KMap.Pixel} pixel 地图容器像素,格式为KMap.Pixel对象,必填
  842. * @returns {KMap.LngLat} 返回KMap.LngLat格式的经纬度
  843. * @memberof Map
  844. */
  845. containerToLngLat(pixel) {
  846. pixel = Common.KMapPixel2MapPixel(pixel)
  847. let lnglat =this.map.getCoordinateFromPixel(pixel)
  848. lnglat = proj.toLonLat(lnglat)
  849. lnglat = Common.MapLngLat2KMapLngLat(lnglat)
  850. return lnglat
  851. }
  852. /**
  853. * @description 经纬度坐标转地图容器屏幕坐标
  854. * @param {KMap.LngLat} lnglat 经纬度坐标,KMap.LngLat格式的经纬度,必填
  855. * @returns {KMap.Pixel} 返回地图容器像素,格式为KMap.Pixel对象
  856. * @memberof Map
  857. */
  858. lngLatToContainer(lnglat) {
  859. lnglat = Common.KMapLngLat2MapLngLat(lnglat)
  860. let coordinate = proj.fromLonLat(lnglat)
  861. let container =this.map.getPixelFromCoordinate(coordinate)
  862. return Common.MapPixel2KMapPixel(container)
  863. }
  864. /**
  865. * @description 获取地图顺时针旋转角度
  866. * @returns {number} 顺时针旋转角度(弧度)
  867. * @memberof Map
  868. */
  869. getRotation() {
  870. let rotation = this.view.getRotation()
  871. return rotation
  872. }
  873. /**
  874. * @description 设置地图顺时针旋转角度
  875. * @param {number} rotation 顺时针旋转角度(弧度),必填
  876. * @memberof Map
  877. */
  878. setRotation(rotation) {
  879. this.view.setRotation(rotation)
  880. }
  881. /**
  882. * @description 获取地图插件集合
  883. * @returns {Array} 地图插件集合数组
  884. * @memberof Map
  885. */
  886. getControls() {
  887. let controls =this.map.getControls().array_
  888. return controls
  889. }
  890. /**
  891. * @description 添加插件
  892. * @param {ol.control} control OL原生control对象
  893. * @memberof Map
  894. */
  895. addControl(control) {
  896. let state = true
  897. let controls = this.map.getControls().array_
  898. for(let i=0; i<controls.length; i++) {
  899. if(control == controls[i]) {
  900. state = false
  901. break
  902. }
  903. }
  904. if(state){
  905. this.map.addControl(control)
  906. }
  907. }
  908. /**
  909. * @description 删除插件
  910. * @param {ol.control} control 插件,必填
  911. * @memberof Map
  912. */
  913. removeControl(control) {
  914. let controls = this.map.getControls().array_
  915. for(let i=0; i<controls.length; i++) {
  916. if(control == controls[i]) {
  917. this.map.removeControl(controls[i])
  918. return
  919. }
  920. }
  921. }
  922. /**
  923. * @description 清空默认插件 注意如果要清除默认插件需要在加载其他插件前调用此函数
  924. * @memberof Map
  925. */
  926. removeOriginControls() {
  927. let controls = this.map.getControls().array_
  928. for(let i=0; i<controls.length; i++) {
  929. this.map.removeControl(controls[i])
  930. }
  931. }
  932. /**
  933. * @description 获取地图指针样式
  934. * @memberof Map
  935. */
  936. getDefaultCursor() {
  937. let mapContainer = this.map.getTargetElement()
  938. let cursor = mapContainer.style.cursor
  939. return cursor
  940. }
  941. /**
  942. * @description 设置地图指针样式
  943. * @param {String} cursorStyle 鼠标样式("default"默认指针,"pointer"小手,"move"移动指针, "text"文本指针,"wait"等待状态,"help"帮助),必填
  944. * @memberof Map
  945. */
  946. setDefaultCursor(cursorStyle) {
  947. let mapContainer = this.map.getTargetElement()
  948. if(cursorStyle != undefined) {
  949. mapContainer.style.cursor = cursorStyle
  950. }
  951. else {
  952. mapContainer.style.cursor = "default"
  953. }
  954. }
  955. /**
  956. * @description 设置鼠标悬停在元素上时的样式
  957. * @param {String} cursorStyle 鼠标样式("default"默认指针,"pointer"小手,"move"移动指针, "text"文本指针,"wait"等待状态,"help"帮助),必填
  958. * @memberof Map
  959. */
  960. setFeatureCursor(cursorStyle) {
  961. cursorStyle = (cursorStyle == undefined)? "default" : cursorStyle
  962. let mapContainer = this.map.getTargetElement()
  963. let defaultCursor = mapContainer.style.cursor
  964. this.map.on("pointermove",function(e){
  965. let features = this.map.forEachFeatureAtPixel(e.pixel,function(feature) { return feature })
  966. if(features) {
  967. mapContainer.style.cursor = cursorStyle
  968. }
  969. else {
  970. mapContainer.style.cursor = defaultCursor
  971. }
  972. })
  973. }
  974. /**
  975. * @description 获取地图显示元素种类
  976. * @returns {Array} 地图显示元素种类集合
  977. * @memberof Map
  978. */
  979. getFeatures() {
  980. const vm = this
  981. let features = new Array()
  982. if(vm.baseLayer.getVisible() == true) {
  983. features.push("Tile")
  984. }
  985. if(vm.markerLayer.getVisible() == true){
  986. features.push("Marker")
  987. }
  988. if(vm.labelLayer.getVisible() == true){
  989. features.push("Label")
  990. }
  991. if(vm.polyLineLayer.getVisible() == true){
  992. features.push("PolyLine")
  993. }
  994. return features
  995. }
  996. /**
  997. * @description 设置地图显示元素种类
  998. * @param {JSON} param param 地图元素显示参数,JSON对象,必填
  999. * param.marker true/false,点标记是否显示,选填
  1000. * param.label true/false,文本标记是否显示,选填
  1001. * param.polyline true/false,线标记是否显示,选填
  1002. * @memberof Map
  1003. */
  1004. setFeatures(param) {
  1005. const vm = this
  1006. if(param.marker == true || param.marker == false){
  1007. vm.markerLayer.setVisible(param.marker)
  1008. }
  1009. if(param.label == true || param.label == false){
  1010. vm.labelLayer.setVisible(param.label)
  1011. }
  1012. if(param.polyline == true || param.polyline == false){
  1013. vm.polyLineLayer.setVisible(param.polyline)
  1014. }
  1015. }
  1016. /**
  1017. * @description 获取地图状态(双击缩放/拖拽/滚动鼠标中间缩放)
  1018. * @returns {JSON} 地图状态
  1019. * {"DoubleClickZoom": true, "DragAndDrop": true, "MouseWheelZoom": true}
  1020. * @memberof Map
  1021. */
  1022. getStates() {
  1023. let interactions =this.map.getInteractions().array_
  1024. let DoubleClickZoom,DragAndDrop,MouseWheelZoom
  1025. for(let i=0; i<interactions.length; i++) {
  1026. if(i==1) DoubleClickZoom = interactions[i].getActive()
  1027. if(i==2) DragAndDrop = interactions[i].getActive()
  1028. if(i==7) MouseWheelZoom = interactions[i].getActive()
  1029. }
  1030. let states = {
  1031. "DoubleClickZoom": DoubleClickZoom,
  1032. "DragAndDrop": DragAndDrop,
  1033. "MouseWheelZoom": MouseWheelZoom
  1034. }
  1035. return states
  1036. }
  1037. /**
  1038. * @description 设置地图状态(双击缩放/拖拽/滚动鼠标中间缩放)
  1039. * @param {JSON} param 地图状态 JSON对象,必填
  1040. * param.DoubleClickZoom true/false(双击缩放地图),选填
  1041. * param.DragAndDrop true/false(地图拖拽),选填
  1042. * param.MouseWheelZoom true/false(滚动鼠标中间缩放地图),选填
  1043. * @memberof Map
  1044. */
  1045. setStates(param) {
  1046. let interactions =this.map.getInteractions().array_
  1047. if(param.DoubleClickZoom == true || param.DoubleClickZoom == false)
  1048. interactions[1].setActive(param.DoubleClickZoom)
  1049. if(param.DragAndDrop == true || param.DragAndDrop == false)
  1050. interactions[2].setActive(param.DragAndDrop)
  1051. if(param.MouseWheelZoom == true || param.MouseWheelZoom == false)
  1052. interactions[7].setActive(param.MouseWheelZoom)
  1053. }
  1054. /**
  1055. * @description 清空地图所有元素
  1056. * @memberof Map
  1057. */
  1058. clearMap() {
  1059. const vm = this
  1060. //清空图层元素
  1061. vm.markerLayer.getSource().clear()
  1062. vm.labelLayer.getSource().clear()
  1063. vm.polyLineLayer.getSource().clear()
  1064. vm.polygonLayer.getSource().clear()
  1065. //清空地图弹窗
  1066. vm.clearInfoWindow()
  1067. }
  1068. /**
  1069. * @description 清除地图对象并清空地图容器(建议少使用此API,容易造成报错)
  1070. * @memberof Map
  1071. */
  1072. destroy() {
  1073. //清空地图对象
  1074. // this.map.destroy()
  1075. //清空地图容器
  1076. let target =this.map.getTargetElement()
  1077. target.innerHTML = ""
  1078. Common.UseBaiDuOnlineLayer = false;
  1079. Common.UseGaoDeOnlineLayer = false;
  1080. Common.UseWGS84OnlineLayer = false;
  1081. }
  1082. /**
  1083. * @description 获取地图图层数组
  1084. * @return {Array} 地图图层数组
  1085. * @memberof Map
  1086. */
  1087. getLayers() {
  1088. let layers =this.map.getLayers().array_
  1089. return layers
  1090. }
  1091. /**
  1092. * @description 设置地图各个图层显示/隐藏
  1093. * @param {JSON} param 地图图层显示参数,JSON对象,必填
  1094. * param.Marker true/false,点标记图层显示/隐藏,选填
  1095. * param.Label true/false,文本标记图层显示/隐藏,选填
  1096. * param.PolyLine true/false,线标记图层显示/隐藏,选填
  1097. * @memberof Map
  1098. */
  1099. setLayers(param) {
  1100. const vm = this
  1101. if(param.Marker == true || param.Marker == false){
  1102. vm.markerLayer.setVisible(param.Marker)
  1103. }
  1104. if(param.Label == true || param.Label == false){
  1105. vm.labelLayer.setVisible(param.Label)
  1106. }
  1107. if(param.PolyLine == true || param.PolyLine == false){
  1108. vm.polyLineLayer.setVisible(param.PolyLine)
  1109. }
  1110. }
  1111. /**
  1112. * @description 获取地图各个图层index值
  1113. * @returns {JSON} JSON对象
  1114. * {"markerLayer": 0, "labelLayer": 0, "polyLineLayer": 0}
  1115. * @memberof Map
  1116. */
  1117. getLayersIndex() {
  1118. const vm = this
  1119. let index = {}
  1120. index.markerLayer = vm.markerLayer.getZIndex()
  1121. index.labelLayer = vm.labelLayer.getZIndex()
  1122. index.polyLineLayer = vm.polyLineLayer.getZIndex()
  1123. return index
  1124. }
  1125. /**
  1126. * @description 设置地图各个图层index值,index值大的图层显示在上方,值相同时后加载的图层显示在上方
  1127. * @param {JSON} param 图层索引JSON对象,必填
  1128. * param.marker 点标记图层index值,选填
  1129. * param.label 文字标记图层index值,选填
  1130. * param.polyLine 线标记图层index值,选填
  1131. * @memberof Map
  1132. */
  1133. setLayersIndex(param) {
  1134. const vm = this
  1135. let markerIndex = (param.marker)? param.marker : vm.markerLayer.getZIndex()
  1136. let labelIndex = (param.label)? param.label : vm.labelLayer.getZIndex()
  1137. let polyLineIndex = (param.polyLine)? param.polyLine : vm.polyLineLayer.getZIndex()
  1138. vm.markerLayer.setZIndex(markerIndex)
  1139. vm.labelLayer.setZIndex(labelIndex)
  1140. vm.polyLineLayer.setZIndex(polyLineIndex)
  1141. }
  1142. /**
  1143. * @description 注册地图事件
  1144. * @param {String} eventName 地图操作事件类型,必填
  1145. * "click":单击地图,双击将触发两次;"singleclick":单击地图;"dblclick":双击地图;"movestart":开始移动地图;
  1146. * "moveend":移动地图结束;"postrender":渲染地图后;"pointerdrag":拖动指针时;"mousemove":移动指针时
  1147. * @param {funciton} callback 操作事件触发时调用的函数,必填
  1148. * @memberof Map
  1149. */
  1150. on(eventName,callback) {
  1151. if(eventName == "mousemove"){
  1152. eventName = "pointermove"
  1153. }
  1154. if(eventName == "load"){
  1155. eventName = "postrender"
  1156. }
  1157. this.map.on(eventName,callback)
  1158. }
  1159. /**
  1160. * @description 注册地图事件(事件仅执行一次)
  1161. * @param {Strig} eventName 地图操作事件类型,必填
  1162. * "click":单击地图,双击将触发两次;"singleclick":单击地图;"dblclick":双击地图;"movestart":开始移动地图;
  1163. * "moveend":移动地图结束;"postrender":渲染地图后;"pointerdrag":拖动指针时;"mousemove":移动指针时
  1164. * @param {function} callback 操作事件触发时调用的函数,必填
  1165. * @memberof Map
  1166. */
  1167. once(eventName,callback) {
  1168. if(eventName == "mousemove"){
  1169. eventName = "pointermove"
  1170. }
  1171. if(eventName == "load"){
  1172. eventName = "postrender"
  1173. }
  1174. this.map.once(eventName,callback)
  1175. }
  1176. /**
  1177. * @description 取消地图绑定事件
  1178. * @param {Strig} eventName 地图操作事件类型,必填
  1179. * "click":单击地图,双击将触发两次;"singleclick":单击地图;"dblclick":双击地图;"movestart":开始移动地图;
  1180. * "moveend":移动地图结束;"postrender":渲染地图后;"pointerdrag":拖动指针时;"mousemove":移动指针时
  1181. * @param {function} callback 操作事件触发时调用的函数,必填
  1182. * @memberof Map
  1183. */
  1184. off(eventName,callback) {
  1185. if(eventName == "mousemove"){
  1186. eventName = "pointermove"
  1187. }
  1188. if(eventName == "load"){
  1189. eventName = "postrender"
  1190. }
  1191. this.map.un(eventName,callback)
  1192. }
  1193. setMarkerLayerZoomInfo(minZoom,maxZoom){
  1194. this.markerLayer.setMaxZoom(maxZoom);
  1195. this.markerLayer.setMinZoom(minZoom);
  1196. }
  1197. setPolylineLayerZoomInfo(minZoom,maxZoom){
  1198. this.polylineLayer.setMaxZoom(maxZoom);
  1199. this.polylineLayer.setMinZoom(minZoom);
  1200. }
  1201. setPolygonLayerZoomInfo(minZoom,maxZoom){
  1202. this.polygonLayer.setMaxZoom(maxZoom);
  1203. this.polygonLayer.setMinZoom(minZoom);
  1204. }
  1205. }
  1206. export default Map