我已经放弃百度地图了,为什么呢?
原因一: 百度地图api太乱不容易查阅
原因二: 百度给出的案例太少,可参考项太少
第三点也是最重要的,百度地图花钱,百度地图花钱,百度地图花钱,
很荣幸,作为国内唯一免费开源大型好用的高德地图成为我的第二个采坑对象。
说说我为什么用nuxt:其实出于私心,我想调研一下nuxt的seo,踩踩nuxt的坑,熟悉一些框架工作流程,以便于后续项目开发;
还有一点是我想把地图抽离出来,来满足公司的各种业务。
好吧,进入正题:
首先,安装nuxt框架:
npx create-nuxt-app gaode-map
安装时会有一些选项,我是如下选择的:
接着安装一些需要的依赖,scss和axios:
sass安装
npm i scss-loader node-scss --save-dev
然后可以在assets下建一个scss文件,如下:
然后在nuxt.config.js引入该文件:
这样就能用scss了,把所有的scss文件导入到index.scss文件中
axios导入:
官方给了方法
那如何通过自定义配置axios呢?在plugins新建axios.js文件,写入如下代码:
import Vue from 'vue' import axios from 'axios'
//中间可以写配置项
Vue.prototype.$axios = axios
然后你应该懂得了
更改服务端口号:
在nuxt.config.js添加如下配置:
server: { port: 8989, // default: 3000 host: '0.0.0.0', // default: localhost, }
接下来来步入正题,导入高德地图
这个有很多种方式,这里介绍两种:
1,全局导入,在nuxt.config.js 里加script标签,将路径和key放在后边(注意要写在head对象里边,类似原生结构)
script: [ {src: "https://webapi.amap.com/maps?v=1.4.15&key=your key"} ]
2.我采用的是这种方式,异步加载地图,除此之外,这种的好处是可以分块加载。我是在plugins目录下新建一个js文件,就叫aMap.js吧,然后写一个类,作为地图的注册
export default function MapLoader() { return new Promise((resolve, reject) => { // 全局对象如果存在地图直接将结果抛出 if (window.AMap) { resolve(window.AMap) } else { // 创建script标签并放入cdn链接 var script = document.createElement('script') script.type = 'text/javascript' script.async = true script.src = 'http://webapi.amap.com/maps?v=1.3&key=your key&callback=initAMap' script.onerror = reject document.head.appendChild(script) } window.initAMap = () => { // 注入相关插件 window.AMap.plugin(['AMap.ToolBar', 'AMap.CircleEditor', 'AMap.PolyEditor'], function () { //异步同时加载多个插件 var toolbar = new AMap.ToolBar(); map.addControl(toolbar); }); // 将结果抛出 resolve(window.AMap) } }) }
然后就可以在组件中调用该类了:
import MapLoader from "@/plugins/aMap.js";mounted() { let that = this; MapLoader().then(AMap => { that.map = new AMap.Map("container", { center: [118.02, 39.63], zoom: 13 }).catch(error => { console.log('地图加载失败',error) }) }
接下来开始搭建地图页面,先来说一下思路,前端负责调用地图组件,画不规则图形,把图形上的点的经纬度给后端,后端查询出该区域里所有的小区返回给前端,这里先接受前端拿到多边形的点经纬度
前端在初始化地图后,在地图里实例化多边形的函数添加到地图,然后点击按钮触发编辑多边形事件,大致代码如下
<template> <div class="index"> <div> <el-button class="btn" @click="polyEditor.open()" style="margin-bottom: 5px">开始编辑</el-button> <el-button class="btn" @click="polyEditor.close()">结束编辑</el-button> </div> <div class="main"> <div class="store-list"> <h3>选中的坐标</h3> <div v-for="(item, index) in alreadeArr" :key=index> {{item}} </div> </div> <div id="container"></div> </div> </div> </template> <script> import MapLoader from "@/plugins/aMap.js"; export default { data() { return { num: 0, polyEditor: {}, alreadeArr: [] }; }, mounted() { let that = this; MapLoader().then(AMap => { that.map = new AMap.Map("container", { center: [118.02, 39.63], zoom: 13 }); var path = [ [118.134005, 39.6339], [118.130915, 39.629607], [118.122575, 39.630397], [118.132575, 39.640397] ] var polygon = new AMap.Polygon({ path: path, strokeColor: "#FF33FF", strokeWeight: 6, strokeOpacity: 0.2, fillOpacity: 0.4, fillColor: '#1791fc', zIndex: 50, }) that.map.add(polygon) // 缩放地图到合适的视野级别 that.map.setFitView([ polygon ]) that.polyEditor = new AMap.PolyEditor(that.map, polygon) // 拖拽点后触发 that.polyEditor.on('adjust', function(event) { let arr = [] let point = polygon.getPath() point.forEach(el => { arr.push({"lat": el.lat, "lon": el.lng}) }) that.alreadeArr = arr console.log('选中的区域',arr) // event.target 即为编辑后的多边形对象 }) }); }, methods: { } }; </script> <style> * { margin: 0; padding: 0; } #container { width: 1400px; height: 900px; margin: 0 auto; box-shadow: 0 0 10px #ccc; } </style>
效果如下:
可以看出前端已经拿到了点坐标(后续功能持续更新)