# atl-map 微信小程序高德、腾讯、百度地图 简易好用的微信小程序地图定位,封装腾讯、高德、百度地图 sdk,atl-map 开箱即用。 支持点击定位获取具体位置信息和经纬度,地图搜索,经纬度解析(逆地理编码:经纬度->地点描述),新增内容插槽支持自定义内容,电子围栏(地图多边形) [atl-map 插件下载](https://ext.dcloud.net.cn/plugin?name=atl-map) ## 使用前准备 在平台创建应用并申请 key ### 申请高德、腾讯、百度地图 key - 高德地图测试 key 申请地址 `https://console.amap.com/dev/key/app` 服务平台选择微信小程序 - 腾讯地图测试 key 申请地址 `https://lbs.qq.com/dev/console/application/mine` 启用产品选择微信小程序 - 百度地图测试 key 申请地址 `https://lbs.baidu.com/apiconsole/key/create#/home` 应用类型选择微信小程序 ** 重要!!! ** 配置文件 `manifest.json` 微信小程序需要开启定位权限配置`requiredPrivateInfos`和`permission` ```json "mp-weixin": { "appid": "xxxx", "usingComponents": true, "requiredPrivateInfos": ["getLocation"],//开启定位权限 "permission": { "scope.userLocation": { "desc": "开启定位权限" } } } ``` ## 基本使用 ### vue 模板 ```vue ``` ### js 代码 ```javascript export default { data() { return { disable: false, show: false, title: '', address: '', longitude: '', latitude: '', imageSrc: '/static/logo.png', //自定义图片 marker: { id: 1, height: 50, width: 40 // iconPath: '/static/comm/position.png' }, // mapKey: '42795f9a59358dea58a8bxxx',//高德地图测试key mapKey: 'ZNJBZ-E6RHJ-EV3F2-DL73K-ARTTH-3EBRZ', //腾讯地图测试key // mapKey: 'p5mGzPEt30bwv1yEkeQGsGP4Xrs9xxxx', //百度地图 mapType: 'tmap' // tmap bmap amap }; }, onLoad() {}, methods: { onClick() { this.show = true; }, confirm(e) { if (e) { this.longitude = e.longitude; this.latitude = e.latitude; this.title = e.title; this.address = e.address; } this.show = false; } } }; ``` ## 电子围栏案例 添加了电子围栏demo,因为使用第三方插件判断是否在范围内,** 重要!!! ** 需要在项目中额外下载 @turf/boolean-point-in-polygon 插件 或者是自己写个方法判断是否在范围内 `npm i @turf/boolean-point-in-polygon` 如果启动报错 `@turf/helpers` 未找到,那请下载 `npm i @turf/helpers` 地区经纬度生成 参考 [DataV.GeoAtlas地理小工具系列](https://datav.aliyun.com/portal/school/atlas/area_selector) 可以选择范围选择器或者边界生成器生成经纬度数据 ### vue 模板 ```vue ``` ### js 代码 ```javascript import booleanPointInPolygon from "@turf/boolean-point-in-polygon"; import { point, polygon } from "@turf/helpers"; export default { data() { return { polygons: [ { points: [ { longitude: "106.57", latitude: "29.52", }, { longitude: "106.57", latitude: "29.53", }, { longitude: "106.55", latitude: "29.53", }, { longitude: "106.55", latitude: "29.52", }, { longitude: "106.57", latitude: "29.52", }, ], strokeWidth: 1, strokeColor: "#ff000066", fillColor: "#ff000016", }, { points: [ { longitude: "106.57", latitude: "29.51", }, { longitude: "106.57", latitude: "29.515", }, { longitude: "106.55", latitude: "29.515", }, { longitude: "106.57", latitude: "29.51", }, ], strokeWidth: 1, strokeColor: "#ff000066", fillColor: "#ff000016", }, ], disable: false, show: false, title: "", address: "", longitude: "", latitude: "", imageSrc: "/static/logo.png", //自定义图片 marker: { id: 1, height: 50, width: 40, // iconPath: '/static/comm/position.png' }, // mapKey: '42795f9a59358dea58a8bxxx',//高德地图测试key mapKey: "ZNJBZ-E6RHJ-EV3F2-DL73K-ARTTH-3EBRZ", //腾讯地图测试key // mapKey: 'p5mGzPEt30bwv1yEkeQGsGP4Xrs9xxxx', //百度地图 mapType: "tmap", // tmap bmap amap }; }, onLoad() {}, methods: { changeMarker(e) { const { latitude, longitude } = e; const _polygons = this.polygons.map((polygon) => { return polygon.points.map((i) => [ Number(i.longitude), Number(i.latitude), ]); }); const _point = point([longitude, latitude]); const _polygon = polygon(_polygons); // 根据电子围栏判断否禁用 this.disable = booleanPointInPolygon(_point, _polygon); }, onClick() { this.show = true; }, confirm(e) { if (e) { this.longitude = e.longitude; this.latitude = e.latitude; this.title = e.title; this.address = e.address; } this.show = false; }, }, }; ``` ### 预览 ![预览图片1](https://raw.githubusercontent.com/13982720426/uniapp-plugin-atl-map/master/static/map1.png) ![预览图片2](https://raw.githubusercontent.com/13982720426/uniapp-plugin-atl-map/master/static/map2.png) ![预览图片3](https://raw.githubusercontent.com/13982720426/uniapp-plugin-atl-map/master/static/map3.png) ## API ### Props | 参数 | 说明 | 类型 | 默认值 | | ------------| ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ---------- | ------------------------------------------------------------------------------------------------- | | mapKey | `必填`,地图 KEY | `String` | 腾讯测试 key(每日限量) | | mapType | `非必填`,地图类型(腾讯:'tmap',高德:'amap',百度:'bmap') | `String` | tmap | | longitude | `非必填`,经度 | `String` | 当前定位 | | latitude | `非必填`,纬度 | `String` | 当前定位 | | marker | `非必填`,点位配置,只支持一个点位 | `Object` | [uniapp map 组件](https://uniapp.dcloud.net.cn/component/map.html#marker)默认值 | | disable | `非必填`,确定按钮是否禁用 | `Boolean` | false | | isPolygons | `非必填`,是否显示多边形(电子围栏) | `Boolean` | false | | polygons | `非必填`,多边形配置(具体配置请看案例或者官网说明) | `Array` | `[]`,[uniapp map 组件](https://uniapp.dcloud.net.cn/component/map.html#marker) polygons 配置说明 | | isCustomBar | `非必填`,是否自定义顶部(一般自定义顶部标题栏时使用) | `Boolean` | false (自定义顶部标题栏时留出[胶囊按钮](https://uniapp.dcloud.net.cn/api/ui/menuButton.html#getmenubuttonboundingclientrect)安全距离) | | top | `非必填`,地图距离顶部位置(一般自定义顶部标题栏时使用) | `String`、`Number` | 原生标题栏时,默认值:0,`"navigationStyle": "custom"`为自定义标题栏时,默认值:30 | | changeMarker| `非必填`,点位变化事件(可以通过 [turf](https://turfjs.fenxianglu.cn/category/booleans/booleanPointInPolygon.html#booleanpointinpolygon) 插件判断是否在电子围栏内,再配合 disable 属性使用,具体使用参考完整 demo) | `Function` | 返回值`{title,latitude,longitude,address,...高德/腾讯/百度地图其他参数}` | | confirm | `非必填`,点击确定事件 | `Function` | 返回值`{title,latitude,longitude,address,...高德/腾讯/百度地图其他参数}` | ### Solt | 名称 | 说明 | 其他 | | ------- | ------------------- | --------------------------------------------------------------------------------------------------------------------------| | content | 自定义 content 内容 | 使用的是 uniapp [cover-view 组件](https://uniapp.dcloud.net.cn/component/cover-view.html#cover-view)小程序注意事项请看官网 | ## 注意事项 1. [腾讯地图 key](https://lbs.qq.com/dev/console/application/mine) 每日限量测试,请自行申请 2. 目前只支持微信小程序,其他平台请下载源码自行测试修改[github 地址](https://github.com/13982720426/uniapp-plugin-atl-map.git) 3. 本项目使用 vue2 语法,vue3 也支持 4. 微信小程序可能需要设置服务器域名,[登录小程序平台](https://mp.weixin.qq.com/wxamp/index/index) 服务器域名 -> request 合法域名(填入用到的平台域名 `https://api.map.baidu.com;https://apis.map.qq.com;https://restapi.amap.com;` 5. 百度地图如果遇到接口返回 `APP Referer校验失败`,在[百度地图控制台](https://lbs.baidu.com/apiconsole/key/create#/home) 删除当前应用,重新创建应用并在 APP ID 填 `*` [参考链接](https://blog.csdn.net/m0_73504190/article/details/131420444) 6. 如果点击地图没有查出数据,请查看微信开发者工具控制台网络(Network),是否有查询接口返回`{"status":200,"message":"APP不存在,AK有误请检查再重试"}、{"status":"0","info":"INVALID_USER_KEY","infocode":"10001"}、{"status": 311, "message": "key格式错误"}`等类似响应数据,多数是地图 key 的问题,更多状态码查看对应地图平台状态码说明文档 7. 完整示例项目使用到了电子围栏,booleanPointInPolygon 等方法使用到了第三方插件,所以下载完整示例项目之后需要 `npm i`安装相应依赖,只下载插件非完整示例项目可以忽略 ## 优化 开发初衷是为了能够支持各平台地图,满足需要不同地图的开发者,但是这会产生其他问题。一个项目一般情况下只用一个平台,没有用到的组件和 SDK 导致代码冗余,占用内存 所以在设计的时候就将``组件设计为一个入口组件,``、``、``为独立的子组件,可插拔。简而言之就是每个子组件可以单独使用,删除不用的组件可以减少体积。 推荐选定自己使用的平台之后,删除其他不用的组件和 SDK。 比如:只用腾讯地图,删除其他地图组件,在`uni_modules/atl-map/components` 下,删除 bmap、amap 文件夹,修改入口文件`atl-map.vue`,只用`tmap`组件 ```vue ``` js 只引入和注册`tmap`组件 ```js