【HarmonyOS 6】地图操作系列-标记详解(Marker)

  • 时间:2025-11-27 22:48 作者: 来源: 阅读:11
  • 扫一扫,手机访问
摘要:简介 标记(Marker)的作用是用来对地图指定位置进行标记标识,或者展示地图相关信息。Marker中封装了大量的触发事件,例如点击事件(on(‘markerClick’))、拖拽事件(on(‘markerDrag’)),方便我们实现各种用户交互。这篇文章不会讲解怎样子申请权限和开通AGC地图权限等,如果有需要,可以查阅之前发布的相关文章。 对于讲述过程的代码是独立出来的,可能会存在不完整性,在

简介


标记(Marker)的作用是用来对地图指定位置进行标记标识,或者展示地图相关信息。Marker中封装了大量的触发事件,例如点击事件(on(‘markerClick’))、拖拽事件(on(‘markerDrag’)),方便我们实现各种用户交互。这篇文章不会讲解怎样子申请权限和开通AGC地图权限等,如果有需要,可以查阅之前发布的相关文章。 对于讲述过程的代码是独立出来的,可能会存在不完整性,在文章的末尾会贴上所有的代码。

这篇文章主要讲解怎样子生成标记和标记的一些用法。

所需权限

ohos.permission.INTERNET 联网需要ohos.permission.LOCATION 定位需要ohos.permission.APPROXIMATELY_LOCATION 定位需要

初始代码

初始界面和相关的辅助类代码。

MarkerPage


import { MarkerViewModel } from '../ViewModels/MarkerViewModel'
import { MapComponent } from '@kit.MapKit'

@Entry
@ComponentV2
struct MarkerPage {
  @Local VM: MarkerViewModel = new MarkerViewModel()

  aboutToAppear(): void {
    this.VM.Init(this.getUIContext())
  }

  build() {
    Column() {
      MapComponent({
        mapOptions: this.VM.MapOption,
        mapCallback: this.VM.MapCallBack
      })
        .width("100%")
        .height("50%")
    }
    .height('100%')
    .width('100%')
  }
}

MarkerViewModel


import { map, mapCommon } from "@kit.MapKit"
import { AsyncCallback } from "@kit.BasicServicesKit"
import { geoLocationManager } from "@kit.LocationKit"
import { Permissions } from "@kit.AbilityKit"
import { PermissionUtils } from "../Utils/PermissionUtils"

@ObservedV2
export class MarkerViewModel {
  /**
   * 地图初始化参数设置
   */
  MapOption?: mapCommon.MapOptions
  /**
   * 地图回调方法
   */
  MapCallBack?: AsyncCallback<map.MapComponentController>
  /**
   * 地图控制器
   */
  MapController?: map.MapComponentController
  /**
   * 地图监听管理器
   */
  MapEventManager?: map.MapEventManager
  /**
   * 所需要得权限
   */
  MapPermissions: Permissions[] =
    [
      'ohos.permission.INTERNET',
      'ohos.permission.LOCATION',
      'ohos.permission.APPROXIMATELY_LOCATION'
    ]
  /**
   * 当前位置的维度
   */
  @Trace LocationLatitude: number = 39.9;
  /**
   * 当前位置的经度
   */
  @Trace LocationLongitude: number = 116.4;
  MyUIContext?: UIContext

  constructor() {
    this.UpdateLocation()
    this.MapOption = {
      //相机位置
      position: {
        target: {
          latitude: this.LocationLatitude,
          longitude: this.LocationLongitude
        },
        zoom: 15
      },
      //地图类型
      mapType: mapCommon.MapType.STANDARD,
      //地图最小图层,默认值为2
      minZoom: 2,
      //地图最大图层,默认值为20
      maxZoom: 20,
      //是否支持旋转手势
      rotateGesturesEnabled: true,
      //是否支持滑动手势
      scrollGesturesEnabled: true,
      //是否支持缩放手势
      zoomGesturesEnabled: true,
      //是否支持倾斜手势
      tiltGesturesEnabled: true,
      //是否展示缩放控件
      zoomControlsEnabled: true,
      //是否展示定位按钮
      myLocationControlsEnabled: true,
      //是否展示指南针控件
      compassControlsEnabled: false,
      //是否展示比例尺
      scaleControlsEnabled: true,
      //是否一直显示比例尺,只有比例尺启用时该参数才生效。
      alwaysShowScaleEnabled: true
    };
    this.MapCallBack = async (err, mapController) => {
      if (!err) {
        this.MapController = mapController;
        //启用我的位置图层
        mapController.setMyLocationEnabled(true);
        //设置我的位置跟随设备移动
        mapController.setMyLocationStyle({
          displayType: mapCommon.MyLocationDisplayType.LOCATE
        })
        //启用我的位置按钮
        mapController.setMyLocationControlsEnabled(true);
        //地图监听时间管理器
        this.MapEventManager = this.MapController.getEventManager();
      }
    }
  }

  public async Init(uiContext: UIContext) {
    this.MyUIContext = uiContext;
    //识别权限是否赋予
    if (!PermissionUtils.CheckPermissions(this.MapPermissions)) {
      const perResult: boolean = await PermissionUtils.RequestPermissions(this.MapPermissions);
      if (!perResult) {
        console.error("用户未授权");
        return;
      }
    }
  }

  /**
   * 更新用户定位
   */
  public async UpdateLocation() {
    // 获取用户位置坐标
    try {
      let location: geoLocationManager.Location = await geoLocationManager.getCurrentLocation();
      const convertPoint = map.convertCoordinateSync(mapCommon.CoordinateType.WGS84,
        mapCommon.CoordinateType.GCJ02, {
          longitude: location.longitude,
          latitude: location.latitude
        });
      this.LocationLongitude = convertPoint.longitude;
      this.LocationLatitude = convertPoint.latitude;
    } catch (error) {
      console.error("更新用户坐标出错");
    }
  }
}

PermissionUtils


import { abilityAccessCtrl, bundleManager, common, Permissions } from '@kit.AbilityKit';

/**
 *权限封装类
 */
export class PermissionUtils {
  /**
   * 检查权限是否授权(完全授权)
   * @param permissionsArr 权限集合
   * @returns true:已经全部授权;false:没有全部授权
   */
  public static CheckPermissions(permissionsArr: Permissions[]): boolean {
    const atManager = abilityAccessCtrl.createAtManager();
    //获取bundle信息
    const bundleInfo =
      bundleManager.getBundleInfoForSelfSync(bundleManager.BundleFlag.GET_BUNDLE_INFO_WITH_APPLICATION);
    // 拿到当前应用的tokenID 标识
    const tokenID = bundleInfo.appInfo.accessTokenId
    //校验应用是否被授予权限
    let result: boolean = true;
    permissionsArr.forEach((x: Permissions, index: number) => {
      if (!(atManager.checkAccessTokenSync(tokenID, x) === abilityAccessCtrl.GrantStatus.PERMISSION_GRANTED)) {
        result = false;
        return;
      }
    })
    return result;
  }

  /**
   * 申请授权(首次弹窗申请)
   * @param permissionList 权限集合
   * @returns true:权限完全加载;false:有权限没有加载
   */
  public static async RequestPermissions(permissionList: Permissions[]): Promise<boolean> {
    // 程序访问控制管理
    const atManager = abilityAccessCtrl.createAtManager();
    // 拉起弹框请求用户授权
    const grantStatus = await atManager.requestPermissionsFromUser(getContext(), permissionList)
    // 获取请求权限的结果
    const isAuth = grantStatus.authResults.every(v => v === abilityAccessCtrl.GrantStatus.PERMISSION_GRANTED)
    // 返回 Promise 授权结果
    return isAuth ? Promise.resolve(true) : Promise.reject(false)
  }

  /**
   * 打开系统设置的权限管理页面
   */
  public static OpenPermissionSettingsPage() {
    // 获取上下文
    const context = getContext() as common.UIAbilityContext
    // 获取包信息
    const bundleInfo = bundleManager.getBundleInfoForSelfSync(bundleManager.BundleFlag.GET_BUNDLE_INFO_WITH_APPLICATION)
    // 打开系统设置页
    context.startAbility({
      bundleName: 'com.huawei.hmos.settings',
      abilityName: 'com.huawei.hmos.settings.MainAbility',
      uri: 'application_info_entry',
      parameters: {
        // 按照包名打开对应设置页
        pushParams: bundleInfo.name
      }
    })
  }
}

页面

根据上面的初始化方法,应该展示出如下页面:

如果没有展示当前页面的,需要排查项目的签名等配置是否正确,权限是否已经开启。

Maker

常用方法

获取标记属性方法

方法返回类型备注
getTitlestring返回标记设定的标题。
getSnippetstring 返回标记设定的子标题。 
getAlphanumber获取标记的透明度
 getPosition  mapCommon.LatLng 获取标记的坐标
getRotationnumber获取标记的旋转角度
isClickableboolean标记是否可以点击。
true:可以;
false:不可以
isDraggableboolean获取标记是否可以通过长按来拖拽。
true:可以;
false:不可以
isFlatboolean标记是否平贴地图.
 isInfoWindowVisible boolean信息窗是否可见。
true:可见;
false:不可见
getAltitudenumber 获取标记的海拔高度。(单位:m) 
isAnnotationVisibleboolean返回标记文本是否可见。

设置标记属性方法

方法 输入参数类型 备注
setAlphanumber设置标记的透明度属性。
setClickableboolean设置标记是否可以点击
setDraggableboolean设置标记是否可以长按拖拽。
setFlatboolean设置标记是否平贴地图。
setIconstring | image.PixelMap | Resource设置标记的图标。
图片格式支持jpg、jpeg、png、gif、webp、svg。
资源相对路径格式:图标存放在resources/rawfile,icon参数传入rawfile文件夹下的相对路径。
toDataURL格式(如data:image/png;base64,<图片的Base64字节编码值>)
setMarkerAnchoranchorU: number,
anchorV: number
设置标记的锚点位置。
锚点是标记图标接触地图平面的点,图标的左顶点为(0, 0)点,右顶点为(1, 0)点,左底点为(0, 1)点,右底点为(1, 1)点.
setPositionmapCommon.LatLng设置标记的位置坐标。
setRotationnumber设置标记的旋转角度,即标记围绕标记锚点顺时针旋转的角度,旋转轴垂直于标记。
默认旋转角度为0,默认位置为北对齐。
setTitlestring设置信息窗的标题。
setSnippetstring设置信息窗口的子标题。
setInfoWindowAnchoranchorU: number, anchorV: number设置信息窗的锚点位置,取值范围:[0, 1],坐标轴和锚点位置一样。
setInfoWindowVisibleboolean设置信息窗是否可见。
true:可见;
flase:不可见
setAnimationAnimation设置标记的动画
startAnimation启动标记的动画。
clearAnimation清除标记的动画。
setAltitudenumber设置海拔高度。
setAnnotationVisibleboolean设置标记是否显示文本。
setIconBuilderCustomBuilder设置生成标记图标的自定义组件。

创建Maker

通过map.MapComponentController的addMarker方法,并传入MarkerOptions对象为参数,在地图上添加一个标记。

标记(Marker)参数(MarkerOptions)

属性类型备注
visibleboolean设置可见性。默认值:true
zIndexnumber标记的叠加顺序,数值越大,越在上层
positionmapcommon.LatLng标记的位置坐标.
rotationnumber标记的旋转角度。
以正北方向为0度、顺时针方向为正的角度,默认值为0
iconstring | image.PixelMap | Resource图标
alphanumber透明度,取值范围[0, 1]
0代表完全透明,1表示完全不透明,默认值为1.
anchorUnumber锚点的水平坐标,以图像宽度的比例
取值范围[0,1]。默认值0.5
anchorVnumber锚点的垂直坐标,以图像高度的比例
取值范围[0,1]。默认值1
clickableboolean标记是否可以点击
默认值:false
draggableboolean是否可以通过长按来拖拽
默认值为false
flatboolean是否平贴地图
titlestring信息窗口的标题,超长字串超出部分用省略号“…”表示。
snippetstring信息窗口的子标题,超长字串超出部分用省略号“…”表示。
infoWindowAnchorUnumber指示标记信息窗口的锚点在水平方向上的位置。
取值范围:[0, 1],默认值为0.5
infoWindowAnchorVnumber指示标记信息窗口的锚点在垂直方向上的位置。
取值范围:[0, 1],默认值为0
altitudenumber海拔高度,单位:米,默认值为0。
collisionRuleCollisionRule地图POI之间的碰撞规则。
NONE:名称和图标都不参与碰撞。
NAME:仅名称参与碰撞。
ALL:图标和名称都参与碰撞。
annotationsText[]标记的注释,最小长度为1,最大长度为3。
showIconboolean是否显示标记的图标,默认值为true。
annotationPositionTextPosition设置点注释的文本位置。
DEFAULT:默认模式
TOP: 文本显示在图标上方。
BOTTOM:文本显示在图标下方。
LEFT:文本显示在图标的左侧。
RIGHT:文本显示在图标的右侧。

添加一个标记(Marker)代码


 /**
   * 在当前位置添加一个标记
   * @param point
   */
  public async CreateLocationMarker() {
    if (this.MapController) {
      // Marker初始化参数
      let markerOptions: mapCommon.MarkerOptions = {
        //定位点
        position: {
          latitude: this.LocationLatitude,
          longitude: this.LocationLongitude
        }
      };
      try {
        let marker: map.Marker = await this.MapController.addMarker(markerOptions);
      } catch (error) {
        console.error(error)
      }
    }
  }

创建一个自定义样式的标记

需求:

选择放置标记的地点。生成图片加下标数量的标记。点击标记,地图的视图聚焦到标记上。

使用sceneMap.chooseLocation选择地点

自定义LocationUtil类和SelectLocationPoint方法,弹出页面并提供位置搜索按钮,方便搜索想要的位置。

originLocationPoint:初始化地图中心点

public static async SelectLocationPoint(uiContext: common.UIAbilityContext,
    originLocationPoint: mapCommon.LatLng): Promise<mapCommon.LatLng | undefined> {
    try {
      let locationChoosingOptions: sceneMap.LocationChoosingOptions = {
        // 地图中心点坐标
        location: originLocationPoint,
        language: 'zh_cn',
        // 展示搜索控件
        searchEnabled: true,
        // 展示附近Poi
        showNearbyPoi: true
      };
      // 拉起地点选取页
      let result: sceneMap.LocationChoosingResult =
        await sceneMap.chooseLocation(uiContext, locationChoosingOptions);
      if (result) {
        return result.location;
      }
      return undefined;
    } catch (e) {
      console.error(`地点选择错误,错误代码:${e}`);
      return undefined;
    }
  }

自定义标记Builder方法

自定一张照片和下标,这里的内容可以自定义哈。但是存在一个问题,值引用时,修改数值时UI无法刷新,需要时间去研究引用的方式,但是我们的标点并不多,每次更新可以直接删除对应的标点重新创建。如果有解决方案的小伙伴也欢迎留言交流哈。


aboutToAppear(): void {
    this.VM.Init(this.getUIContext(), () => {
      this.MyMarkerBuilder(this.VM.MarkerList.length);
    })
  }


@Builder
  MyMarkerBuilder(index: number) {
    RelativeContainer() {
      Image($r('app.media.app_icon'))
        .width(30)
        .height(30)
        .syncLoad(true)
      Text(`${index}`)
        .fontSize(10)
        .width(15)
        .textAlign(TextAlign.Center)
        .height(15)
        .backgroundColor($r('app.color.Main_Color'))
        .borderRadius(7.5)
        .alignRules({
          bottom: { anchor: "__container__", align: VerticalAlign.Bottom },
          right: { anchor: "__container__", align: HorizontalAlign.End }
        })
    }
    .width(30)
    .height(30)
  }

MarkerViewModel.ets

通过CustomBuilder对象的方式传递,并修改选择地点生成标记的方法


  /**
   * 标记builder
   */
  @Trace MarkerBuilder?: CustomBuilder
  
    /**
   * 标记集合
   */
  @Trace MarkerList: map.Marker[] = []
  
  public async Init(uiContext: UIContext, markerBuilder: CustomBuilder) {
    this.MyUIContext = uiContext;
    this.MarkerBuilder = markerBuilder;
    //识别权限是否赋予
    if (!PermissionUtils.CheckPermissions(this.MapPermissions)) {
      const perResult: boolean = await PermissionUtils.RequestPermissions(this.MapPermissions);
      if (!perResult) {
        console.error("用户未授权");
        return;
      }
    }
  }
  
  /**
   * 选择地点,并生成标记
   */
  public async SelectedLocationCreateMarker() {
    if (this.MyUIContext && this.MapController) {
      let selectResult =
        await LocationUtil.SelectLocationPoint(this.MyUIContext.getHostContext() as common.UIAbilityContext, {
          latitude: this.LocationLatitude,
          longitude: this.LocationLongitude
        })
      if (selectResult) {
        // Marker初始化参数
        let markerOptions: mapCommon.MarkerOptions = {
          //定位点
          position: selectResult,
          iconBuilder: this.MarkerBuilder
        };
        try {
          let marker: map.Marker = await this.MapController.addMarker(markerOptions);
          this.MarkerList.push(marker);
        } catch (error) {
          console.error(error)
        }
      }
    }
  }

点击标记,地图的视图聚焦到标记

需要订阅标记点击方法的监听事件。移动地图的相机位置。

代码实现

使用map.MapEventManager对象监听标记点击事件,建议可以在一开始的时候直接注入监听


this.MapEventManager.on("markerClick", (marker: map.Marker) => {
          this.MarkerClickCallBack(marker);
        });
        
        
  /**
   * 标记点击事件
   * @param marker
   */
  public async MarkerClickCallBack(marker: map.Marker) {
    let locationPoint: mapCommon.LatLng = marker.getPosition();
    this.MoveCamera(locationPoint.latitude, locationPoint.longitude);
  }

  /**
   * 移动视图相机
   * @param latitude 维度
   * @param longitude 经度
   */
  public async MoveCamera(latitude: number, longitude: number) {
    if (this.MapController) {
      //将视图移动到标点位置
      let nwPosition = map.newCameraPosition({
        target: {
          latitude: latitude,
          longitude: longitude
        },
        zoom: 18
      })
      // 以动画方式移动地图相机
      this.MapController.animateCamera(nwPosition, 1000);
    }
  }

效果展示

自定义标记完整代码


MarkerPage.ets


import { MarkerViewModel } from '../ViewModels/MarkerViewModel'
import { MapComponent } from '@kit.MapKit'

@Entry
@ComponentV2
struct MarkerPage {
  @Local VM: MarkerViewModel = new MarkerViewModel()

  aboutToAppear(): void {
    this.VM.Init(this.getUIContext(), () => {
      this.MyMarkerBuilder(this.VM.MarkerList.length);
    })
  }

  build() {
    Column({ space: 10 }) {
      MapComponent({
        mapOptions: this.VM.MapOption,
        mapCallback: this.VM.MapCallBack
      })
        .width("100%")
        .height("50%")
      Button("创建一个标记")
        .onClick((event: ClickEvent) => {
          this.VM.CreateLocationMarker()
        })
      Button("选择地点创建标记")
        .onClick((event: ClickEvent) => {
          this.VM.SelectedLocationCreateMarker()
        })
    }
    .height('100%')
    .width('100%')
  }

  @Builder
  MyMarkerBuilder(index: number) {
    RelativeContainer() {
      Image($r('app.media.app_icon'))
        .width(30)
        .height(30)
        .syncLoad(true)
      Text(`${index}`)
        .fontSize(10)
        .width(15)
        .textAlign(TextAlign.Center)
        .height(15)
        .backgroundColor($r('app.color.Main_Color'))
        .borderRadius(7.5)
        .alignRules({
          bottom: { anchor: "__container__", align: VerticalAlign.Bottom },
          right: { anchor: "__container__", align: HorizontalAlign.End }
        })
    }
    .width(30)
    .height(30)
  }
}

MarkerViewModel.ets


import { map, mapCommon } from "@kit.MapKit"
import { AsyncCallback } from "@kit.BasicServicesKit"
import { geoLocationManager } from "@kit.LocationKit"
import { common, Permissions } from "@kit.AbilityKit"
import { PermissionUtils } from "../Utils/PermissionUtils"
import { LocationUtil } from "../Utils/LocationUtil"

@ObservedV2
export class MarkerViewModel {
  /**
   * 地图初始化参数设置
   */
  MapOption?: mapCommon.MapOptions
  /**
   * 地图回调方法
   */
  MapCallBack?: AsyncCallback<map.MapComponentController>
  /**
   * 地图控制器
   */
  MapController?: map.MapComponentController
  /**
   * 地图监听管理器
   */
  MapEventManager?: map.MapEventManager
  /**
   * 所需要得权限
   */
  MapPermissions: Permissions[] =
    [
      'ohos.permission.INTERNET',
      'ohos.permission.LOCATION',
      'ohos.permission.APPROXIMATELY_LOCATION'
    ]
  /**
   * 当前位置的维度
   */
  @Trace LocationLatitude: number = 39.9;
  /**
   * 当前位置的经度
   */
  @Trace LocationLongitude: number = 116.4;
  MyUIContext?: UIContext
  /**
   * 标记builder
   */
  @Trace MarkerBuilder?: CustomBuilder
  /**
   * 标记集合
   */
  @Trace MarkerList: map.Marker[] = []

  constructor() {
    this.UpdateLocation()
    this.MapOption = {
      //相机位置
      position: {
        target: {
          latitude: this.LocationLatitude,
          longitude: this.LocationLongitude
        },
        zoom: 15
      },
      //地图类型
      mapType: mapCommon.MapType.STANDARD,
      //地图最小图层,默认值为2
      minZoom: 2,
      //地图最大图层,默认值为20
      maxZoom: 20,
      //是否支持旋转手势
      rotateGesturesEnabled: true,
      //是否支持滑动手势
      scrollGesturesEnabled: true,
      //是否支持缩放手势
      zoomGesturesEnabled: true,
      //是否支持倾斜手势
      tiltGesturesEnabled: true,
      //是否展示缩放控件
      zoomControlsEnabled: true,
      //是否展示定位按钮
      myLocationControlsEnabled: true,
      //是否展示指南针控件
      compassControlsEnabled: false,
      //是否展示比例尺
      scaleControlsEnabled: true,
      //是否一直显示比例尺,只有比例尺启用时该参数才生效。
      alwaysShowScaleEnabled: true
    };
    this.MapCallBack = async (err, mapController) => {
      if (!err) {
        this.MapController = mapController;
        //启用我的位置图层
        mapController.setMyLocationEnabled(true);
        //设置我的位置跟随设备移动
        mapController.setMyLocationStyle({
          displayType: mapCommon.MyLocationDisplayType.LOCATE
        })
        //启用我的位置按钮
        mapController.setMyLocationControlsEnabled(true);
        //地图监听时间管理器
        this.MapEventManager = this.MapController.getEventManager();
        this.MapEventManager.on("markerClick", (marker: map.Marker) => {
          this.MarkerClickCallBack(marker);
        });
      }
    }
  }

  public async Init(uiContext: UIContext, markerBuilder: CustomBuilder) {
    this.MyUIContext = uiContext;
    this.MarkerBuilder = markerBuilder;
    //识别权限是否赋予
    if (!PermissionUtils.CheckPermissions(this.MapPermissions)) {
      const perResult: boolean = await PermissionUtils.RequestPermissions(this.MapPermissions);
      if (!perResult) {
        console.error("用户未授权");
        return;
      }
    }

  }

  /**
   * 更新用户定位
   */
  public async UpdateLocation() {
    // 获取用户位置坐标
    try {
      let location: geoLocationManager.Location = await geoLocationManager.getCurrentLocation();
      const convertPoint = map.convertCoordinateSync(mapCommon.CoordinateType.WGS84,
        mapCommon.CoordinateType.GCJ02, {
          longitude: location.longitude,
          latitude: location.latitude
        });
      this.LocationLongitude = convertPoint.longitude;
      this.LocationLatitude = convertPoint.latitude;
    } catch (error) {
      console.error("更新用户坐标出错");
    }
  }

  /**
   * 在当前位置添加一个标记
   * @param point
   */
  public async CreateLocationMarker() {
    if (this.MapController) {
      // Marker初始化参数
      let markerOptions: mapCommon.MarkerOptions = {
        //定位点
        position: {
          latitude: this.LocationLatitude,
          longitude: this.LocationLongitude
        },
        clickable: true
      };
      try {
        let marker: map.Marker = await this.MapController.addMarker(markerOptions);
      } catch (error) {
        console.error(error)
      }
    }
  }

  /**
   * 选择地点,并生成标记
   */
  public async SelectedLocationCreateMarker() {
    if (this.MyUIContext && this.MapController) {
      let selectResult =
        await LocationUtil.SelectLocationPoint(this.MyUIContext.getHostContext() as common.UIAbilityContext, {
          latitude: this.LocationLatitude,
          longitude: this.LocationLongitude
        })
      if (selectResult) {
        // Marker初始化参数
        let markerOptions: mapCommon.MarkerOptions = {
          //定位点
          position: selectResult,
          iconBuilder: this.MarkerBuilder,
          clickable: true
        };
        try {
          let marker: map.Marker = await this.MapController.addMarker(markerOptions);
          this.MarkerList.push(marker);
        } catch (error) {
          console.error(error)
        }
      }
    }
  }

  /**
   * 移动视图相机
   * @param latitude 维度
   * @param longitude 经度
   */
  public async MoveCamera(latitude: number, longitude: number) {
    if (this.MapController) {
      //将视图移动到标点位置
      let nwPosition = map.newCameraPosition({
        target: {
          latitude: latitude,
          longitude: longitude
        },
        zoom: 18
      })
      // 以动画方式移动地图相机
      this.MapController.animateCamera(nwPosition, 1000);
    }
  }

  /**
   * 标记点击事件
   * @param marker
   */
  public async MarkerClickCallBack(marker: map.Marker) {
    let locationPoint: mapCommon.LatLng = marker.getPosition();
    this.MoveCamera(locationPoint.latitude, locationPoint.longitude);
  }
}

PermissionUtils.ets


import { abilityAccessCtrl, bundleManager, common, Permissions } from '@kit.AbilityKit';

/**
 *权限封装类
 */
export class PermissionUtils {
  /**
   * 检查权限是否授权(完全授权)
   * @param permissionsArr 权限集合
   * @returns true:已经全部授权;false:没有全部授权
   */
  public static CheckPermissions(permissionsArr: Permissions[]): boolean {
    const atManager = abilityAccessCtrl.createAtManager();
    //获取bundle信息
    const bundleInfo =
      bundleManager.getBundleInfoForSelfSync(bundleManager.BundleFlag.GET_BUNDLE_INFO_WITH_APPLICATION);
    // 拿到当前应用的tokenID 标识
    const tokenID = bundleInfo.appInfo.accessTokenId
    //校验应用是否被授予权限
    let result: boolean = true;
    permissionsArr.forEach((x: Permissions, index: number) => {
      if (!(atManager.checkAccessTokenSync(tokenID, x) === abilityAccessCtrl.GrantStatus.PERMISSION_GRANTED)) {
        result = false;
        return;
      }
    })
    return result;
  }

  /**
   * 申请授权(首次弹窗申请)
   * @param permissionList 权限集合
   * @returns true:权限完全加载;false:有权限没有加载
   */
  public static async RequestPermissions(permissionList: Permissions[]): Promise<boolean> {
    // 程序访问控制管理
    const atManager = abilityAccessCtrl.createAtManager();
    // 拉起弹框请求用户授权
    const grantStatus = await atManager.requestPermissionsFromUser(getContext(), permissionList)
    // 获取请求权限的结果
    const isAuth = grantStatus.authResults.every(v => v === abilityAccessCtrl.GrantStatus.PERMISSION_GRANTED)
    // 返回 Promise 授权结果
    return isAuth ? Promise.resolve(true) : Promise.reject(false)
  }

  /**
   * 打开系统设置的权限管理页面
   */
  public static OpenPermissionSettingsPage() {
    // 获取上下文
    const context = getContext() as common.UIAbilityContext
    // 获取包信息
    const bundleInfo = bundleManager.getBundleInfoForSelfSync(bundleManager.BundleFlag.GET_BUNDLE_INFO_WITH_APPLICATION)
    // 打开系统设置页
    context.startAbility({
      bundleName: 'com.huawei.hmos.settings',
      abilityName: 'com.huawei.hmos.settings.MainAbility',
      uri: 'application_info_entry',
      parameters: {
        // 按照包名打开对应设置页
        pushParams: bundleInfo.name
      }
    })
  }
}

LocationUtil.ets


import { common, Permissions } from "@kit.AbilityKit";
import { geoLocationManager } from "@kit.LocationKit";
import { map, mapCommon, sceneMap } from "@kit.MapKit";

export class LocationUtil {
  /**
   * 当前位置的维度
   */
  public static LocationLatitude: number = 39.9;
  /**
   * 当前位置的经度
   */
  public static LocationLongitude: number = 116.4;
  /**
   * 所需要得权限
   */
  public static MapPermissions: Permissions[] =
    [
      'ohos.permission.INTERNET',
      'ohos.permission.LOCATION',
      'ohos.permission.APPROXIMATELY_LOCATION'
    ]

  /**
   * 更新用户定位
   */
  public static async UpdateLocation() {
    // 获取用户位置坐标
    let location: geoLocationManager.Location = await geoLocationManager.getCurrentLocation();
    const convertPoint = map.convertCoordinateSync(mapCommon.CoordinateType.WGS84,
      mapCommon.CoordinateType.GCJ02, {
        longitude: location.longitude,
        latitude: location.latitude
      });
    LocationUtil.LocationLongitude = convertPoint.longitude
    LocationUtil.LocationLatitude = convertPoint.latitude;
  }

  /**
   * 选择地图
   * @param uiContext
   * @returns
   */
  public static async SelectLocation(uiContext: common.UIAbilityContext): Promise<sceneMap.LocationChoosingResult | undefined> {
    try {
      await LocationUtil.UpdateLocation();
      let locationChoosingOptions: sceneMap.LocationChoosingOptions = {
        // 地图中心点坐标
        location: { latitude: LocationUtil.LocationLatitude, longitude: LocationUtil.LocationLongitude },
        language: 'zh_cn',
        // 展示搜索控件
        searchEnabled: true,
        // 展示附近Poi
        showNearbyPoi: true
      };
      // 拉起地点选取页
      let result: sceneMap.LocationChoosingResult =
        await sceneMap.chooseLocation(uiContext, locationChoosingOptions);
      return result;
    } catch (e) {
      console.info(e)
      return undefined;
    }

  }

  public static async SelectLocationPoint(uiContext: common.UIAbilityContext,
    originLocationPoint: mapCommon.LatLng): Promise<mapCommon.LatLng | undefined> {
    try {
      let locationChoosingOptions: sceneMap.LocationChoosingOptions = {
        // 地图中心点坐标
        location: originLocationPoint,
        language: 'zh_cn',
        // 展示搜索控件
        searchEnabled: true,
        // 展示附近Poi
        showNearbyPoi: true
      };
      // 拉起地点选取页
      let result: sceneMap.LocationChoosingResult =
        await sceneMap.chooseLocation(uiContext, locationChoosingOptions);
      if (result) {
        return result.location;
      }
      return undefined;
    } catch (e) {
      console.error(`地点选择错误,错误代码:${e}`);
      return undefined;
    }
  }
}
  • 全部评论(0)
最新发布的资讯信息
【系统环境|】创建一个本地分支(2025-12-03 22:43)
【系统环境|】git 如何删除本地和远程分支?(2025-12-03 22:42)
【系统环境|】2019|阿里11面+EMC+网易+美团面经(2025-12-03 22:42)
【系统环境|】32位单片机定时器入门介绍(2025-12-03 22:42)
【系统环境|】从 10 月 19 日起,GitLab 将对所有免费用户强制实施存储限制(2025-12-03 22:42)
【系统环境|】价值驱动的产品交付-OKR、协作与持续优化实践(2025-12-03 22:42)
【系统环境|】IDEA 强行回滚已提交到Master上的代码(2025-12-03 22:42)
【系统环境|】GitLab 15.1发布,Python notebook图形渲染和SLSA 2级构建工件证明(2025-12-03 22:41)
【系统环境|】AI 代码审查 (Code Review) 清单 v1.0(2025-12-03 22:41)
【系统环境|】构建高效流水线:CI/CD工具如何提升软件交付速度(2025-12-03 22:41)
手机二维码手机访问领取大礼包
返回顶部