鸿蒙ArtTS 中如何实现地图打卡功能 比如公司打卡 文章配置完整代码

一、首先要拿到自己的定位信息

csharp 复制代码
this.location = await geoLocationManager.getCurrentLocation()
  • 打开权限,一行代码拿到定位信息,核心API是geoLocationManager
  • 这里的经纬度是我们判断是否可以打卡成功的关键。

二、画地图(华为地图)

  • 拿到公司的经纬度信息进行Marker标记,进行相关配置
  • 然后在公司的经纬度上进行Circle画圆,进行相关配置(假设半径为500)
kotlin 复制代码
import { MapComponent, mapCommon, map } from '@kit.MapKit';
import { AsyncCallback } from '@kit.BasicServicesKit';
import { abilityAccessCtrl, Permissions } from '@kit.AbilityKit';
import { geoLocationManager } from '@kit.LocationKit';
import { promptAction } from '@kit.ArkUI';

@Entry
@Component
struct HuaweiMapDemo {
  @State location:geoLocationManager.Location | null = null
  @State b:number = 0
  private TAG = "HuaweiMapDemo";
  private mapOptions?: mapCommon.MapOptions;
  private callback?: AsyncCallback<map.MapComponentController>;
  private mapController?: map.MapComponentController;
  private mapEventManager?: map.MapEventManager;
  private marker?: map.Marker;
  private mapCircle?: map.MapCircle;

  async aboutToAppear(){
    this.requestPermissions(["ohos.permission.LOCATION","ohos.permission.APPROXIMATELY_LOCATION"])
    // 地图初始化参数,设置地图中心点坐标及层级
    this.mapOptions = {
      position: {
        target: {
          latitude: 22.19,
          longitude: 114.11
        },
        zoom: 10
      },
      myLocationControlsEnabled: true,
      alwaysShowScaleEnabled:true
    };

    // 地图初始化的回调
    this.callback = async (err, mapController) => {
      if (!err) {
        // 获取地图的控制器类,用来操作地图
        this.mapController = mapController;
        let location = await geoLocationManager.getCurrentLocation();
        this.mapController.setMyLocation(location);
        // 启用我的位置图层
        this.mapController.setMyLocationEnabled(true);
        // 启用我的位置按钮
        this.mapController.setMyLocationControlsEnabled(true);
        // let style: mapCommon.MyLocationStyle = {
        //   anchorU: 0.5,
        //   anchorV: 0.5,
        //   radiusFillColor: 0xffff0000,
        //   // icon为自定义图标资源,使用时需要替换
        //   // 图标存放在resources/rawfile,icon参数传入rawfile文件夹下的相对路径
        //   icon: 'images/logo.png'
        // };
        // await this.mapController.setMyLocationStyle(style);

        this.mapEventManager = this.mapController.getEventManager();
        //this.mapEventManager.on("myLocationButtonClick", callback);
        // Marker初始化参数
        let markerOptions: mapCommon.MarkerOptions = {
          position: {
            latitude: 22.64,
            longitude: 113.92
          },
          rotation: 0,
          visible: true,
          zIndex: 0,
          alpha: 1,
          anchorU: 0.5,
          anchorV: 1,
          clickable: true,
          draggable: true,
          flat: false,
          // 图标存放在resources/rawfile,icon参数传入rawfile文件夹下的相对路径
          icon: 'images/head.png'
        };
        // 创建Marker
        this.marker = await this.mapController.addMarker(markerOptions);
        // 设置信息窗的标题
        this.marker.setTitle('深圳');
        // 设置信息窗的子标题
        this.marker.setSnippet('小黑程序员');
        // 设置标记可点击
        this.marker.setClickable(true);
        // 设置信息窗的锚点位置
        this.marker.setInfoWindowAnchor(1, 1);
        // 设置信息窗可见
        this.marker.setInfoWindowVisible(true);
        // 地图加载完成事件
        let callback = () => {
          console.info(this.TAG, `on-mapLoad`);
        }
        this.mapEventManager.on("mapLoad", callback);
        let mapCircleOptions: mapCommon.MapCircleOptions = {
          center: {
            latitude: 22.64,
            longitude: 113.92
          },
          radius: 564,
          clickable: true,
          fillColor: 0XFFFFC100,
          strokeColor: 0xFFFF0000,
          strokeWidth: 10,
          visible: true,
          zIndex: 15
        }
        this.mapCircle = await this.mapController.addCircle(mapCircleOptions);
      }
    };
    // let markerOptions:mapCommon.MarkerOptions = {
    //   position:{latitude:39.9,longitude:116.4}
    // }
    // let marker:map.Marker = await this.mapController?.addMarker(markerOptions)
    // marker.
  }
  async requestPermissions(permissions:Permissions[]){
    const atManager = abilityAccessCtrl.createAtManager()
    const requestResult = await atManager.requestPermissionsFromUser(getContext(),permissions)
    const isAuth=requestResult.authResults.every(item=>item===abilityAccessCtrl.GrantStatus.PERMISSION_GRANTED)
    return isAuth === true ? Promise.resolve(true) : Promise.reject(false)
  }

  // 页面每次显示时触发一次,包括路由过程、应用进入前台等场景,仅@Entry装饰的自定义组件生效
  onPageShow(): void {
    // 将地图切换到前台
    if (this.mapController) {
      this.mapController.show();
    }
  }

  // 页面每次隐藏时触发一次,包括路由过程、应用进入后台等场景,仅@Entry装饰的自定义组件生效
  onPageHide(): void {
    // 将地图切换到后台
    if (this.mapController) {
      this.mapController.hide();
    }
  }

  build() {
    Stack({ alignContent: Alignment.Center }) {
      Text(this.b+'当前的位置信息:'+JSON.stringify(this.location,null,2))
        .position({ x: 0, y: 0 })
        .zIndex(99)
      Button('打卡')
        .zIndex(99)
        .position({ x: 20, y: 20 }) // 调整按钮位置
        .onClick(async()=>{
          let fromLatLng: mapCommon.LatLng = {
            latitude: 22.64,
            longitude: 113.92
          };
          this.location = await geoLocationManager.getCurrentLocation()
          const toLatLng: mapCommon.LatLng = {
            latitude: this.location.latitude,
            longitude: this.location.longitude
          }
          let distance = map.calculateDistance(fromLatLng, toLatLng);
          this.b = distance
          if(564 > distance){
            promptAction.showToast({message:'打卡成功'})
            //发送服务器
          }else{
            promptAction.showToast({message:'打卡失败'})
          }
        })
      // 调用MapComponent组件初始化地图
      MapComponent({ mapOptions: this.mapOptions, mapCallback: this.callback }).width('100%').height('100%');
    }.height('100%').width('100%')

  }
}

三、点击按钮判断是否可以打卡成功

四、或者先判断是否可以打卡成功来显示对应的按钮状态

这个逻辑是一样的

注:使用CalculateDistance获得的距离和你用Circle画的圆可能会有出入

相关推荐
KjPrime1 小时前
纯vue手写流程组件
前端·javascript·vue.js
码农不惑3 小时前
前端开发:Vue以及Vue的路由
前端·javascript·vue.js
阿旭哟嘿4 小时前
鸿蒙 元服务摘要
华为·harmonyos
烛阴5 小时前
JavaScript instanceof:你真的懂它吗?
前端·javascript
琢磨先生David5 小时前
鸿蒙开源硬件:重构万物智联生态的底层基座与未来机遇
harmonyos·鸿蒙
shadouqi5 小时前
1.angular介绍
前端·javascript·angular.js
痴心阿文6 小时前
React如何导入md5,把密码password进行md5加密
前端·javascript·react.js
hdk19936 小时前
Edge浏览器登录微软账户报错0x80190001的解决办法
前端·microsoft·edge
徐同保6 小时前
yarn 装包时 package里包含[email protected]报错
前端·javascript