index.js 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690
  1. (() => {
  2. // 初始地图
  3. const initMap = (map) => {
  4. return {
  5. map,
  6. async loadImage(args) {
  7. const { file, minWidth, minHeight } = args
  8. args.img = args.img
  9. ? args.img
  10. : await blobImageLoad(file, minWidth, minHeight)
  11. return loadImageLayer(map, args)
  12. },
  13. screenToLatlan({x, y}) {
  14. const real = map.getCoordinateFromPixel([x, y])
  15. const latlan = ol.proj.transform(real,'EPSG:3857','EPSG:4326')
  16. return latlan
  17. }
  18. }
  19. }
  20. const loadImageLayer = (map, args) => {
  21. const {
  22. lon,
  23. lat
  24. } = args
  25. const itude = ol.proj.fromLonLat([lon, lat])
  26. const { image: imageLayer, canvas } = loadImage(map, args, itude)
  27. map.addLayer(imageLayer);
  28. map.getView().setCenter(
  29. ol.proj.fromLonLat([lon, lat])
  30. );
  31. map.getView().setZoom(19)
  32. return canvas
  33. }
  34. // 经纬度转canvas坐标
  35. const itudeToCanvasPos = (map, extent, itude) => {
  36. //Canvas四至范围不同于当前地图四至范围,计算出南北方向与东西方向的偏移
  37. const mapExtent = map.getView()
  38. .calculateExtent(map.getSize())
  39. //当前底图视图范围的投影坐标
  40. const canvasOrigin = map.getPixelFromCoordinate(
  41. [ extent[0], extent[3] ]
  42. );
  43. //添加到地图上的canvas图像的左上角
  44. const mapOrigin = map.getPixelFromCoordinate(
  45. [ mapExtent[0], mapExtent[3] ]
  46. );
  47. const delta = [
  48. mapOrigin[0] - canvasOrigin[0],
  49. mapOrigin[1] - canvasOrigin[1]
  50. ];
  51. const leftTop = map.getPixelFromCoordinate(itude)
  52. return {
  53. x: leftTop[0] + delta[0],
  54. y: leftTop[1] + delta[1]
  55. }
  56. }
  57. // 平移,旋转,放大当前canvas
  58. const transformCanvasCall = (
  59. canvas,
  60. transform,
  61. oper,
  62. center = {
  63. x: 0,
  64. y: 0
  65. }
  66. ) => {
  67. const ctx = canvas.getContext('2d')
  68. const {
  69. translate,
  70. scale,
  71. rotate
  72. } = transform
  73. ctx.translate(center.x, center.y)
  74. translate && ctx.translate(translate.x, translate.y)
  75. rotate && ctx.rotate(rotate * (Math.PI / 180))
  76. scale && ctx.scale(scale[0], scale[1])
  77. oper && oper()
  78. // scale && ctx.scale(1 / scale, 1 / scale)
  79. // rotate && ctx.rotate(-rotate * (Math.PI / 180))
  80. // translate && ctx.translate(-translate.x, -translate.y)
  81. ctx.translate(-center.x, -center.y)
  82. }
  83. const genImgCanvasItudeToReal = (map, canvas, extent) =>
  84. (itude) => {
  85. return genImgCanvasPosToReal(map, canvas)(
  86. itudeToCanvasPos(map, extent, itude)
  87. )
  88. }
  89. const genImgCanvasPosToReal = (map, canvas) =>
  90. (pos) => {
  91. const $real = map.getViewport()
  92. const offsetWidth = (canvas.width - $real.offsetWidth) / 2
  93. const offsetHeight = (canvas.height - $real.offsetHeight) / 2
  94. return {
  95. x: pos.x - offsetWidth,
  96. y: pos.y - offsetHeight
  97. }
  98. }
  99. const genImgCanvasTransfrom = (canvas, arrayImgs, scale, initPos) =>
  100. (transform) => {
  101. const ctx = canvas.getContext('2d');
  102. const dscale = transform.scale || [1, 1]
  103. const resize = 1 / (scale * 10)
  104. const doScale = [
  105. resize * dscale[0],
  106. resize * dscale[1]
  107. ]
  108. const imgData = { width: 0, height: 0 }
  109. arrayImgs.forEach(imgs => {
  110. let height = 0
  111. imgs.forEach(([img]) => height += img.height)
  112. imgData.width += imgs[0][0].width
  113. if (imgData.height < height) {
  114. imgData.height = height
  115. }
  116. })
  117. initPos.x -= imgData.width / 2
  118. initPos.y -= imgData.height / 2
  119. // , translate: { x: -(imgData.width / 2) * doScale[0], y: -(imgData.height / 2) * doScale[1] }
  120. ctx.fillStyle = 'rgba(0,0,0,0.1)'
  121. ctx.fillRect(0,0, canvas.width, canvas.height)
  122. transformCanvasCall(
  123. canvas,
  124. { ...transform, scale: doScale },
  125. () => {
  126. transform.draw && transform.draw(ctx)
  127. let width = 0
  128. arrayImgs.forEach(imgs => {
  129. let height = 0
  130. imgs.forEach(([img]) => {
  131. ctx.drawImage(img, width, height)
  132. height += img.height
  133. })
  134. width += imgs[0][0].width
  135. })
  136. },
  137. transform.center
  138. )
  139. const move = {
  140. x: transform.translate.x - initPos.x,
  141. y: transform.translate.y - initPos.y,
  142. }
  143. const start = {
  144. x: initPos.x + move.x,
  145. y: initPos.y + move.y,
  146. }
  147. const end = {
  148. x: start.x + imgData.width * doScale[0],
  149. y: start.y + imgData.height * doScale[1],
  150. }
  151. canvas.position = [
  152. start,
  153. end,
  154. Math.abs(start.x - end.x) / resize,
  155. Math.abs(start.y - end.y) / resize
  156. ]
  157. canvas.resize = resize
  158. canvas.imgData = imgData
  159. canvas.imgBox = [
  160. canvas.posToReal(start),
  161. canvas.posToReal(end),
  162. Math.abs(start.x - end.x),
  163. Math.abs(start.y - end.y)
  164. ]
  165. }
  166. // 加载url
  167. const loadImage = (map, args, itude) => {
  168. const canvas = document.createElement('canvas');
  169. const imageCanvas = new ol.source.ImageCanvas({
  170. canvasFunction(extent, scale, _2, size) {
  171. console.log('-------------')
  172. const pos = itudeToCanvasPos(map, extent, itude)
  173. const imgData = { width: 0, height: 0 }
  174. args.img.forEach(imgs => {
  175. let height = 0
  176. imgs.forEach(([img]) => height += img.height)
  177. imgData.width += imgs[0][0].width
  178. if (imgData.height < height) {
  179. imgData.height = height
  180. }
  181. })
  182. console.log(scale)
  183. // pos.x -= imgData.width / 2 * scale
  184. // pos.y -= imgData.height / 2 * scale
  185. canvas.width = size[0];
  186. canvas.height = size[1]
  187. canvas.posToReal = genImgCanvasPosToReal(map, canvas);
  188. canvas.transform = genImgCanvasTransfrom(canvas, args.img, scale, pos, imageCanvas);
  189. canvas.itudeToReal = genImgCanvasItudeToReal(map, canvas, extent)
  190. canvas.transform({
  191. ...args,
  192. translate: {
  193. x: (args.translate ? args.translate.x : 0) + pos.x,
  194. y: (args.translate ? args.translate.y : 0) + pos.y
  195. }
  196. })
  197. return canvas;
  198. }
  199. })
  200. const image = new ol.layer.Image({ source: imageCanvas })
  201. canvas.imageLayer = imageCanvas
  202. return {
  203. image,
  204. canvas
  205. }
  206. }
  207. // 返回本地url
  208. const blobImageLoad = (arrayImages, minWidth, minHeight) => {
  209. console.log(arrayImages)
  210. const analysis = (blob) => new Promise((resolve, reject) => {
  211. const url = window.URL.createObjectURL(blob);
  212. const img = new Image()
  213. img.onload = () => {
  214. if (img.width < minWidth || img.height < minHeight) {
  215. reject('图片宽高需要大于512')
  216. } else {
  217. resolve([img, url, blob])
  218. }
  219. }
  220. img.src = url
  221. })
  222. let arrasPromises = []
  223. for (let images of arrayImages) {
  224. let analys = []
  225. for (let bolb of images) {
  226. analys.push(analysis(bolb))
  227. }
  228. arrasPromises.push(
  229. Promise.all(analys)
  230. )
  231. }
  232. return Promise.all(arrasPromises)
  233. }
  234. // 获取逆转矩阵
  235. const getCanvasInverImatrix = $canvas => {
  236. const ctx = $canvas.getContext('2d')
  237. const transform = ctx.getTransform()
  238. return transform.invertSelf();
  239. }
  240. // canvas坐标转屏幕坐标
  241. const getCanvasToScreenPos = ($canvas, {x, y}) => {
  242. const {
  243. a, b, c,
  244. d, e, f
  245. } = getCanvasInverImatrix($canvas)
  246. const screenX = (c * y - d * x + d * e - c * f) / (b * c - a * d)
  247. const screenY = (y - screenX * b - f) / d
  248. return {
  249. x: Math.round(screenX),
  250. y: Math.round(screenY),
  251. }
  252. }
  253. // 屏幕坐标转canvas坐标
  254. const getScreenToCanvasPos = ($canvas, {x, y}) => {
  255. const {
  256. a, b, c,
  257. d, e, f
  258. } = getCanvasInverImatrix($canvas)
  259. return {
  260. x: Math.round(x * a + y * c + e),
  261. y: Math.round(x * b + y * d + f)
  262. };
  263. }
  264. Vue.component('imageTranform', {
  265. props: ['mapOl'],
  266. name: 'imageTranform',
  267. template: `
  268. <div class="transform-layer" @mousemove.stop.prevent="move" @mouseup="upMove">
  269. <div class="upload-layer">
  270. 目录:<input type="file" @change="imageChange" directory webkitdirectory multiple>
  271. 单文件:<input type="file" @change="imageChange">
  272. </div>
  273. <div class="ctrls" :style="boxStyle" @mousedown.stop.prevent="startMove($event, 'move')"></div>
  274. <div class="cctrls" v-if="box.tl">
  275. <span class="tl" :style="{left: box.tl.x + 'px', top: box.tl.y + 'px'}" @mousedown.prevent.stop="startMove($event, 'scale', 'tl')"></span>
  276. <span class="tc" :style="{left: box.tc.x + 'px', top: box.tc.y + 'px'}" @mousedown.prevent.stop="startMove($event, 'scale', 'tc')"></span>
  277. <span class="tr" :style="{left: box.tr.x + 'px', top: box.tr.y + 'px'}" @mousedown.prevent.stop="startMove($event, 'scale', 'tr')"></span>
  278. <span class="rc" :style="{left: box.rc.x + 'px', top: box.rc.y + 'px'}" @mousedown.prevent.stop="startMove($event, 'scale', 'rc')"></span>
  279. <span class="lc" :style="{left: box.lc.x + 'px', top: box.lc.y + 'px'}" @mousedown.prevent.stop="startMove($event, 'scale', 'lc')"></span>
  280. <span class="br" :style="{left: box.br.x + 'px', top: box.br.y + 'px'}" @mousedown.prevent.stop="startMove($event, 'scale', 'br')"></span>
  281. <span class="bl" :style="{left: box.bl.x + 'px', top: box.bl.y + 'px'}" @mousedown.prevent.stop="startMove($event, 'scale', 'bl')"></span>
  282. <span class="bc" :style="{left: box.bc.x + 'px', top: box.bc.y + 'px'}" @mousedown.prevent.stop="startMove($event, 'scale', 'bc')"></span>
  283. <span class="cc" :style="{left: box.cc.x + 'px', top: box.cc.y + 'px'}" @mousedown.prevent.stop="startMove($event, 'rotate')"></span>
  284. </div>
  285. <div class="box-info" v-if="boxPos.tl">
  286. <div v-for="(item, key) in boxPos" :key="key">
  287. <span>{{key}}</span>
  288. <span>{{item}}</span>
  289. </div>
  290. </div>
  291. </div>
  292. `,
  293. data() {
  294. return {
  295. isHover: false,
  296. box: {},
  297. left: 0,
  298. top: 0
  299. }
  300. },
  301. methods: {
  302. async imageChange(e) {
  303. let imagesArray = []
  304. if (e.target.files.length > 1) {
  305. const formatError = () => {
  306. e.target.value = null
  307. console.log(imagesXYZ)
  308. alert('目录不规范 请上传 z/x/y.png 格式目录,且在最底级目录放置图片文件')
  309. }
  310. let imagesXYZ = {}
  311. for (let file of e.target.files) {
  312. let locals = file.webkitRelativePath.split(/[\\|//]/)
  313. if (locals.length < 3) return formatError()
  314. let current = imagesXYZ
  315. for (let i = 0; i < locals.length; i++) {
  316. let dir = locals[i]
  317. if (i !== locals.length - 1) {
  318. if (!current[dir]) {
  319. current[dir] = i === locals.length - 2 ? [] : {}
  320. }
  321. current = current[dir]
  322. if (i === locals.length - 3) {
  323. current.key = 'z'
  324. }
  325. }
  326. if (i === locals.length - 1) {
  327. current.push(file)
  328. }
  329. }
  330. }
  331. (function analysis (updateXYZ) {
  332. if (updateXYZ.key === 'z') {
  333. imagesXYZ = updateXYZ
  334. return;
  335. }
  336. const names = Object.keys(updateXYZ).sort((a, b) => b - a)
  337. names.forEach(key => {
  338. if (key !== names[0]) {
  339. delete updateXYZ[key]
  340. }
  341. })
  342. analysis(updateXYZ[names[0]])
  343. })(imagesXYZ);
  344. if (!(imagesXYZ && imagesXYZ.key === 'z' && !Array.isArray(imagesXYZ))) {
  345. return formatError()
  346. }
  347. for (let key in imagesXYZ) {
  348. if (!Array.isArray(imagesXYZ[key]) && key !== 'key') {
  349. return formatError()
  350. }
  351. }
  352. delete imagesXYZ.key
  353. Object.keys(imagesXYZ).sort((a, b) => a - b).forEach(key => {
  354. imagesArray.push(
  355. imagesXYZ[key].sort((a, b) => parseInt(a.name) - parseInt(b))
  356. )
  357. })
  358. } else {
  359. imagesArray = [[e.target.files[0]]]
  360. }
  361. try {
  362. this.transfroms = []
  363. this.args = {
  364. draw: (ctx) => {
  365. this.transfroms.forEach(transform => {
  366. transform.forEach(({translate, scale, rotate, center}) => {
  367. // 设置绘制颜色
  368. center && ctx.translate(center.x, center.y)
  369. translate && ctx.translate(translate.x, translate.y)
  370. rotate && ctx.rotate(rotate * (Math.PI / 180))
  371. scale && ctx.scale(scale[0], scale[1])
  372. center && ctx.translate(-center.x, -center.y)
  373. // if (center) {
  374. // ctx.fillStyle = "geend";
  375. // // 绘制成矩形
  376. // ctx.fillRect(center.x, center.y, 100, 100);
  377. // }
  378. })
  379. })
  380. setTimeout(() => {
  381. this.updateBox(this.imgCanvas.imgBox)
  382. })
  383. },
  384. file: imagesArray,
  385. lon: 113.59963069739054,
  386. lat: 22.364821730960752,
  387. translate: {x: 0, y: 0},
  388. scale: [1, 1],
  389. direction: 0
  390. }
  391. console.log('---0---')
  392. this.imgCanvas = await this.map.loadImage(this.args)
  393. } catch(e) {
  394. alert(e)
  395. }
  396. },
  397. updateBox() {
  398. const calcPos = pos => getCanvasToScreenPos(this.imgCanvas, pos)
  399. this.box = {
  400. tl: this.imgCanvas.posToReal(calcPos({x: 0, y: 0})),
  401. tc: this.imgCanvas.posToReal(calcPos({x: this.imgCanvas.imgData.width / 2, y: 0})),
  402. tr: this.imgCanvas.posToReal(calcPos({x: this.imgCanvas.imgData.width, y: 0})),
  403. rc: this.imgCanvas.posToReal(calcPos({x: this.imgCanvas.imgData.width, y: this.imgCanvas.imgData.height / 2})),
  404. lc: this.imgCanvas.posToReal(calcPos({x: 0, y: this.imgCanvas.imgData.height / 2})),
  405. br: this.imgCanvas.posToReal(calcPos({x: this.imgCanvas.imgData.width, y: this.imgCanvas.imgData.height})),
  406. bl: this.imgCanvas.posToReal(calcPos({x: 0, y: this.imgCanvas.imgData.height})),
  407. bc: this.imgCanvas.posToReal(calcPos({x: this.imgCanvas.imgData.width / 2, y: this.imgCanvas.imgData.height})),
  408. cc: this.imgCanvas.posToReal(calcPos({x: this.imgCanvas.imgData.width / 2, y: this.imgCanvas.imgData.height / 2})),
  409. }
  410. let maxX = this.box.tl.x
  411. let minX = this.box.tl.x
  412. let maxY = this.box.tl.y
  413. let minY = this.box.tl.y
  414. Object.values(this.box).forEach(({x, y}) => {
  415. x > maxX && (maxX = x)
  416. y > maxY && (maxY = y)
  417. x < minX && (minX = x)
  418. y < minY && (minY = y)
  419. })
  420. this.box.width = Math.abs(maxX - minX)
  421. this.box.height = Math.abs(maxY - minY)
  422. },
  423. mapStartHandle() {
  424. this.mapDown = true
  425. },
  426. moveHandle(e) {
  427. if (!this.imgCanvas || !this.imgCanvas.imgBox) {
  428. return;
  429. }
  430. if (this.moveing && this.oper) {
  431. this.move(e)
  432. } else {
  433. this.mapDown && this.imgCanvas.imageLayer.refresh()
  434. // const [start, end] = this.box
  435. // this.isHover = e.clientX > start.x && e.clientX < end.x &&
  436. // e.clientY > start.y && e.clientY < end.y
  437. }
  438. },
  439. startMove(ev, oper, dir) {
  440. this.startTransform = {
  441. ...this.args
  442. }
  443. this.transfroms.push([])
  444. this.moveing = true
  445. this.oper = oper
  446. this.dir = dir
  447. this.startMovePos = {
  448. x: ev.clientX,
  449. y: ev.clientY
  450. }
  451. },
  452. move(ev) {
  453. if (!this.moveing) return;
  454. const transfrom = this.transfroms[this.transfroms.length - 1]
  455. const start = getScreenToCanvasPos(
  456. this.imgCanvas,
  457. this.startMovePos
  458. )
  459. const end = getScreenToCanvasPos(
  460. this.imgCanvas,
  461. { x: ev.clientX, y: ev.clientY }
  462. )
  463. const move = {
  464. x: end.x - start.x,
  465. y: end.y - start.y
  466. }
  467. if (this.oper === 'move') {
  468. transfrom.push({ translate: move })
  469. } else if (this.oper === 'scale'){
  470. const width = this.imgCanvas.position[2]
  471. const height = this.imgCanvas.position[3]
  472. let xScale, yScale
  473. switch(this.dir) {
  474. case 'tl':
  475. xScale = (width - move.x) / width
  476. yScale = (height - move.y) / height
  477. if (xScale > 0.1 && yScale > 0.1) {
  478. transfrom.push({
  479. scale: [xScale, yScale],
  480. center: {x: this.imgCanvas.position[2], y: this.imgCanvas.position[3]}
  481. })
  482. }
  483. break;
  484. case 'tc':
  485. yScale = (height - move.y) / height
  486. if (yScale > 0.1) {
  487. transfrom.push({
  488. scale: [1, yScale],
  489. center: {x: 0, y: this.imgCanvas.position[3]}
  490. })
  491. }
  492. break;
  493. case 'tr':
  494. xScale = (width + move.x) / width
  495. yScale = (height - move.y) / height
  496. if (xScale > 0.1 && yScale > 0.1) {
  497. transfrom.push({
  498. scale: [xScale, yScale],
  499. center: {x: 0, y: this.imgCanvas.position[3]}
  500. })
  501. }
  502. break;
  503. case 'rc':
  504. xScale = (width + move.x) / width
  505. if (xScale > 0.1) {
  506. transfrom.push({
  507. scale: [xScale, 1],
  508. center: {x: 0, y: this.imgCanvas.position[3]}
  509. })
  510. }
  511. break;
  512. case 'lc':
  513. xScale = (width - move.x) / width
  514. if (xScale > 0.1) {
  515. transfrom.push({
  516. scale: [xScale, 1],
  517. center: {x: this.imgCanvas.position[2], y: this.imgCanvas.position[3]}
  518. })
  519. }
  520. break;
  521. case 'br':
  522. xScale = (width + move.x) / width
  523. yScale = (height + move.y) / height
  524. if (xScale > 0.1 && yScale > 0.1) {
  525. transfrom.push({
  526. scale: [xScale, yScale],
  527. center: {x: 0, y: 0}
  528. })
  529. }
  530. break;
  531. case 'bl':
  532. xScale = (width - move.x) / width
  533. yScale = (height + move.y) / height
  534. if (xScale > 0.1 && yScale > 0.1) {
  535. transfrom.push({
  536. scale: [xScale, yScale],
  537. center: {x: this.imgCanvas.position[2], y: 0}
  538. })
  539. }
  540. break;
  541. case 'bc':
  542. yScale = (height + move.y) / height
  543. if (yScale > 0.1) {
  544. transfrom.push({
  545. scale: [1, yScale],
  546. center: {x: 0, y: 0}
  547. })
  548. }
  549. break;
  550. }
  551. } else if (this.oper === 'rotate') {
  552. let move = ev.clientX - this.startMovePos.x
  553. let height = this.imgCanvas.position[3]
  554. let width = this.imgCanvas.position[2]
  555. let center = {x: width / 2, y: height / 2}
  556. // let zrotate = transfrom.
  557. transfrom.push({
  558. rotate: move / 3,
  559. center: center
  560. })
  561. }
  562. this.startMovePos = {
  563. x: ev.clientX,
  564. y: ev.clientY
  565. }
  566. this.imgCanvas.imageLayer.refresh()
  567. },
  568. upMove() {
  569. this.moveing = false
  570. this.mapDown = false
  571. this.oper = null
  572. this.dir = null
  573. this.startMovePos = null
  574. },
  575. getInfo() {
  576. return {
  577. pos: this.boxPos,
  578. img: this.args.img
  579. }
  580. }
  581. },
  582. computed: {
  583. boxStyle() {
  584. if (this.box && Object.keys(this.box).length) {
  585. const box = this.box
  586. return {
  587. width: box.width + 20 + 'px',
  588. height: box.height + 20 + 'px',
  589. left: box.cc.x + 'px',
  590. top: box.cc.y + 'px'
  591. }
  592. } else {
  593. return {}
  594. }
  595. },
  596. boxPos() {
  597. if (this.box && Object.keys(this.box).length) {
  598. const ret = {}
  599. for (let key in this.box) {
  600. if (key !== 'width' && key !== 'height') {
  601. ret[key] = this.map.screenToLatlan(this.box[key])
  602. }
  603. }
  604. return ret
  605. } else {
  606. return {}
  607. }
  608. }
  609. },
  610. mounted() {
  611. document.documentElement.addEventListener('mousemove', ev => {
  612. ev.stopPropagation()
  613. ev.preventDefault()
  614. this.moveHandle.bind(this)(ev)
  615. this.move.bind(this)(ev)
  616. })
  617. document.documentElement.addEventListener('mousedown', ev => {
  618. this.mapStartHandle.bind(this)(ev)
  619. })
  620. document.documentElement.addEventListener('mouseup', ev => {
  621. ev.stopPropagation()
  622. ev.preventDefault()
  623. this.upMove.bind(this)()
  624. })
  625. this.map = initMap(this.mapOl)
  626. }
  627. })
  628. })();