HarmonyOS 鸿蒙Next生态下的Map Kit地图服务:功能、应用场景及开发者指南

发布于 1周前 作者 phonegap100 来自 鸿蒙OS

HarmonyOS 鸿蒙Next生态下的Map Kit地图服务:功能、应用场景及开发者指南
<markdown _ngcontent-xpg-c237="" class="markdownPreContainer">

地图服务简介

Map Kit作为鸿蒙OS的一个关键组件,为开发者提供了强大的地图技术。它支持高度定制化的地图显示、高效搜索和智能路线规划等功能。此外,其庞大的兴趣点(PoI)数据库为应用开发提供了广泛的场景和创意空间。

核心特点:

个性化地图显示:根据PoI的属性和区域差异,动态调整地图展示细节。 流畅的手势交互:支持缩放、旋转、移动、倾斜等操作。

应用场景分析

Map Kit适用于多种应用场景,从基础地图创建到复杂的位置搜索和路径规划。

主要应用方向:

地图创建:快速构建具有各种地理元素的个性化地图。 地点搜索:提供灵活且强大的地点搜索功能,覆盖广泛的PoI信息。 路径规划:支持多种出行方式的智能路径规划,优化用户出行体验。

关键功能详述

Map Kit的核心在于其丰富的交互功能和高自由度的地图定制能力。

重要功能点:

地图交互:实现平滑的地图操控体验,增强用户互动。 地图绘制:允许在地图上添加标记、覆盖层和绘制图形,以强化地图的信息表达。 导航与搜索:通过花瓣地图实现详细的导航和内容搜索,满足不同出行需求。

开发前置条件

为了使用AppGallery Connect(简称AGC),我们需要首先在AGC平台上创建一个项目。同时,我们必须在本地准备一个相应的项目工程。例如,我们这里创建了一个名为Chapter0807的工程,旨在帮助开发者掌握华为支付服务的功能。重要的是,确保工程的包名与在AppGallery Connect创建应用时使用的包名完全相同。 AGC(AppGallery Connect)配置流程 特别要注意的是:Bundle name(包名)需要与AGC创建应用时的应用包名一致,这里以com.nutpi.chapter0807为例。 接下来,我将回忆一下如何在DevEco Studio中创建本地工程: 本地工程创建流程

方式一:当DevEco Studio没有打开任何工程时,你可以在欢迎页选择“Create Project”来打开新工程创建向导。

方式二:如果已经打开了一个工程,你可以通过菜单栏选择“File > New > Create Project”来打开新工程创建向导。 注意:在创建新工程时,确保Bundle name(包名)与AGC创建应用时的应用包名保持一致。 按照这些步骤,你可以顺利地在本地创建一个新的项目工程,并确保它的配置与AGC平台上的项目设置相匹配,从而顺利地进行华为支付服务的开发和集成。

Project Create

图 3-9-1 项目创建

AGC(AppGallery Connect)创建流程

步骤一:项目创建

  1. 登录到AppGallery Connect(简称AGC)平台。
  2. 点击“我的项目”选项,进入项目列表页面。
  3. 在项目列表页面中,点击“添加项目”按钮。
  4. 输入你想要的项目名称,然后点击“创建并继续”以进入下一步。

步骤二:添加应用

  1. 项目创建完成之后,进入项目设置页面。
  2. 在项目设置页面中,点击“添加应用”按钮。
  3. 在“添加应用”页面中,你需要设置相关的应用参数。
  4. 确认所填写的应用包名与你在DevEco Studio中创建的HarmonyOS应用工程的Bundle name一致,例如:com.nutpi.chapter0807。
  5. 在选择应用分类时,请选择“应用”。
  6. 完成上述步骤后,点击“确认”以完成应用的添加。

注意:确保应用包名与你的HarmonyOS应用工程的Bundle name完全一致,这是确保应用能够正确集成和运行的关键。 按照这些步骤,你可以顺利地在AGC上创建项目并添加应用,为接下来在HarmonyOS平台上开发和发布你的应用做好准备。

AGC平台

图 3-9-2 AGC平台

应用添加页面

图 3-9-3 AGC 应用添加页面

添加公钥指纹

当应用需要集成如Account Kit(华为账号服务)、Call Kit(通话服务)、Game Service Kit(游戏服务)、Health Service Kit(运动健康服务)、IAP Kit(应用内支付服务)、Live View Kit(实况窗服务)、Map Kit(地图服务)、Payment Kit(华为支付服务)和Push Kit(推送服务)等华为开放能力时,为了确保应用能够正常调试和运行,必须在开发者平台预先添加公钥指纹。

开通地图服务

在AGC平台上,为了启用地图服务并管理相关API,你可以按照以下步骤进行操作:

  1. 登录到AGC平台,并进入“我的应用”页面。
  2. 寻找并点击需要地图服务的应用,然后进入该应用的管理页面。
  3. 在应用管理页面中,找到并点击“API管理”选项。这将带你进入该应用的API管理界面,此处列出了所有已启用和可用的API。
  4. 在API管理界面的搜索框中,输入关键词“map”,系统将会展示与地图服务相关的API选项。
  5. 从搜索结果中找到“地图服务”相关的API,根据实际需求点击相应的选项来启用或管理该服务。 通过以上步骤,可以轻松地在AGC平台上为指定的应用开启和配置地图服务API,进一步丰富应用功能并提升用户体验。

AGC API 选项能力管理页

图 3-9-4 AGC API 选项能力管理页

地图开发指导

MapComponent作为地图组件,其主要功能是在应用页面中嵌入地图显示。通过使用MapComponent,能够实现地图的展示和基础操作,提升用户的空间定位体验。 MapComponentController是地图组件的核心功能入口类,它提供了一套完整的接口和方法,用于操作和管理地图。这个类涵盖了与地图相关的所功能,为开发者提供了一个集中的处理点。其功能主要包括:

  1. 地图类型切换:支持在不同的地图类型之间切换,例如从标准地图切换到卫星视图或空白地图等,满足不同场景下的地图显示需求。
  2. 改变地图状态:允许开发者调整地图的中心点坐标和缩放级别,以控制地图的显示区域和细节层级。
  3. 添加点标记(Marker):在地图上添加标记点,可用于标注特定位置,如商家、景点或用户自定义的地点。
  4. 绘制几何图形:支持在地图上绘制各种几何形状,包括线条(MapPolyline)、多边形(MapPolygon)和圆形(MapCircle)等,这些功能适用于路径规划、区域划分等应用场景。
  5. 各类事件监听:提供了一系列事件监听器,使得开发者可以响应用户的交互操作,如点击、缩放、拖动等,进一步增强应用的互动性。

通过继承MapComponentController类,开发者可以方便地集成和定制地图功能,打造出符合业务需求的地图应用。

图 3-9-5 控制地图效果图

MapComponent 接口说明

地图组件是HarmonyOS应用中用于展示和操作地图的核心部分,它为开发者提供了丰富的功能和接口,以便在应用中实现地理位置的可视化和相关操作。以下是地图组件的两个关键部分的详细解释:

  1. MapOptions: MapOptions类提供了Map组件初始化时所需的属性配置。通过这个类,开发者可以在创建地图时定义一系列的参数,如地图的中心点坐标、缩放级别、是否显示缩略图等。这些属性决定了地图初始化时的外观和行为,使得开发者能够根据具体的应用场景定制地图的初始状态。

  2. MapComponentController: MapComponentController是地图组件的主要功能入口类,它集成了与地图操作相关的各种方法。作为一个中心化的接口,MapComponentController允许开发者方便地访问和控制地图的各种功能,包括但不限于:

o更改地图的视觉样式,如切换不同的地图类型(标准地图、卫星地图等)。

o调整地图的显示状态,包括设置中心点坐标、缩放级别,以及旋转角度等。

o绘制几何图形,如线条(Polyline)、多边形(Polygon)和圆形(Circle),以表示路径、区域等。

o 管理地图上的覆盖物,如信息窗口(InfoWindow)和自定义组件。

o 设置和响应地图的事件监听器,以处理用户的交互动作,如点击、拖动和缩放等。

通过使用这两个类,开发者可以完全掌控地图的初始化设置和后续的操作,实现个性化的地图应用,并提升最终用户的使用体验。

3.9.4地图呈现开发步骤

  1. 导入Map Kit相关模块。
import { map, mapCommon, MapComponent } from '[@kit](/user/kit).MapKit';
import { AsyncCallback } from '[@kit](/user/kit).BasicServicesKit';
<button style="position: absolute; padding: 4px 8px 0px; cursor: pointer; top: 4px; right: 8px; font-size: 14px;">复制</button>
  1. 新建地图初始化参数mapOption,设置地图中心点坐标及层级。通过callback回调的方式获取MapComponentController对象,用操作地图。
调用MapComponent组件,传入mapOption和callback参数,初始化地图。
import { promptAction } from '[@kit](/user/kit).ArkUI';
[@Entry](/user/Entry) [@Component](/user/Component)
  struct Index {
    options?: mapCommon.MapOptions
    callback?: AsyncCallback<map.MapComponentController>
    ctrl?: map.MapComponentController
    aboutToAppear(): void {
      this.options = {
        position: {
          target: {
            latitude: 2.922865,
            longitude: 101.58584
          },
          zoom: 10
        }
          this.callback = async (e, ctrl) => {
        if (!e) {
          this.ctrl = ctrl
          this.ctrl.on('mapLoad', () => {
            promptAction.showToast({
              message: '地图加载中',
              duration: 5000
            })
          })
        }
      }
    }
    build(){
      Row(){
        MapComponent({
          mapOptions: this.options
          ,mapCallback: this.callback
        })
          .width('100%')
          .height('100%')
      }
      .width('100%')
        .height('100%')
    }
  }
<button style="position: absolute; padding: 4px 8px 0px; cursor: pointer; top: 4px; right: 8px; font-size: 14px;">复制</button>

实现效果

最终实现效果

图 3-9.6 最终实现效果

我的位置

我的位置功能主要由MapComponentController的方法实现。以下是各个方法的详细说明:

  1. setMyLocationEnabled(myLocationEnabled: boolean): void 这个方法用于开启或关闭“我的位置”图层功能。当设置为true时,地图将使用系统的连续定位能力显示用户位置。默认情况下,“我的位置”按钮会显示在地图的右下角。点击该按钮后,屏幕中心将以蓝色圆点的形式显示当前定位。

  2. setMyLocationControlsEnabled(enabled: boolean): void 这个方法用于设置是否启用“我的位置”按钮。当设置为true时,按钮将显示在地图上。但是,如果未开启“我的位置”图层功能,点击按钮将不会有任何反应。

  3. setMyLocation(location: geoLocationManager.Location): void 这个方法用于设置“我的位置”坐标。传入一个geoLocationManager.Location对象,以指定用户的位置。

  4. setMyLocationStyle(style: mapCommon.MyLocationStyle): Promise 这个方法用于设置“我的位置”样式。传入一个mapCommon.MyLocationStyle对象,以自定义用户位置的显示样式。该方法返回一个Promise,表示样式设置完成后的操作。

  5. on(type: 'myLocationButtonClick', callback: Callback): void 这个方法用于监听“我的位置”按钮的点击事件。当按钮被点击时,回调函数将被触发。

    ctrl.setMyLocationControlsEnabled(true); // 设置是否启用“我的位置”按钮。
    ctrl.setMyLocationEnabled(true); // 我的位置”图层功能开关
    <button style="position: absolute; padding: 4px 8px 0px; cursor: pointer; top: 4px; right: 8px; font-size: 14px;">复制</button>

我的位置权限

在启用“我的位置”功能之前,确保您的应用已获得用户的定位权限至关重要。您可以通过以下方式获取用户定位:

申请ohos.permission.LOCATION和ohos.permission.APPROXIMATELY_LOCATION权限。需要在module.json5配置文件中声明所需的权限,以确保在运行时能够获得精确的位置信息。

requestPermissions": [
  {
    "name": "ohos.permission.LOCATION",
    "reason": "$string:module_desc",
    "usedScene": {
    }
  },
  {
    "name": "ohos.permission.APPROXIMATELY_LOCATION",
    "reason": "$string:module_desc",
    "usedScene": {
    }
  }
],
<button style="position: absolute; padding: 4px 8px 0px; cursor: pointer; top: 4px; right: 8px; font-size: 14px;">复制</button>

请求权限及代码示例 这段代码是一个使用ArkTS和ArkUI编写的地图应用,主要功能是检查和请求定位权限。以下是对代码的详细解释:

  1. 导入所需的库和类型定义:从[@kit](/user/kit).AbilityKit中导入abilityAccessCtrl、bundleManager、common、PermissionRequestResult和Permissions;从[@kit](/user/kit).BasicServicesKit中导入BusinessError。
  2. 定义一个异步函数checkPermissions(),用于检查应用是否已经获得了定位权限。它首先创建一个包含两个权限(精确定位和大致定位)的数组,然后遍历这个数组,调用checkAccessToken()方法检查每个权限是否被授予。如果某个权限被授予,它会启用地图的定位图层和按钮,并返回true。如果没有任何一个权限被授予,函数返回false。
  3. 定义一个函数requestPermissions(),用于在没有获得定位权限时向用户申请权限。它首先创建一个权限管理器对象,然后调用requestPermissionsFromUser()方法请求定位权限。如果申请成功,它会启用地图的定位图层;如果申请失败,它会输出错误信息。
  4. 定义一个异步函数checkAccessToken(),用于检查应用是否被授予了指定的权限。它首先创建一个权限管理器对象,然后获取应用程序的accessTokenID。接着,它调用checkAccessToken()方法检查指定权限是否被授予,并返回检查结果。
  5. 定义一个函数aboutToAppear(),用于在地图加载时执行一系列操作。它设置一个回调函数,当地图加载完成时,显示一个提示信息,然后调用checkPermissions()函数检查定位权限,并根据需要调用requestPermissions()函数申请权限。 ``` // 导入map模块,包含map、mapCommon和MapComponent import { map, mapCommon, MapComponent } from '[@kit](/user/kit).MapKit'; // 导入AsyncCallback模块,用于异步回调处理 import { AsyncCallback } from '[@kit](/user/kit).BasicServicesKit'; // 导入promptAction模块,用于弹出提示框 import { promptAction } from '[@kit](/user/kit).ArkUI'; // 导入abilityAccessCtrl模块,用于控制应用的权限访问 import { abilityAccessCtrl, bundleManager, common, PermissionRequestResult, Permissions } from '[@kit](/user/kit).AbilityKit'; // 导入BusinessError模块,用于处理业务错误 import { BusinessError } from '[@kit](/user/kit).BasicServicesKit';

[@Entry](/user/Entry) [@Component](/user/Component) struct Index { options?: mapCommon.MapOptions callback?: AsyncCallback<map.MapComponentController> ctrl?: map.MapComponentController

aboutToAppear(): void {
  this.options = {
    position: {
      target: {
        latitude: 2.922865,
        longitude: 101.58584
      },
      zoom: 10
    }
  }

this.callback = async (e, ctrl) => { if (!e) { this.ctrl = ctrl

  <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.ctrl.<span class="hljs-literal"><span class="hljs-literal">on</span></span><span class="hljs-function"><span class="hljs-params"><span class="hljs-function"><span class="hljs-params">(</span></span><span class="hljs-string"><span class="hljs-function"><span class="hljs-params"><span class="hljs-string">'mapLoad'</span></span></span></span><span class="hljs-function"><span class="hljs-params">, async () =&gt; {
    promptAction.showToast({
      message: </span></span><span class="hljs-string"><span class="hljs-function"><span class="hljs-params"><span class="hljs-string">'地图加载中'</span></span></span></span><span class="hljs-function"><span class="hljs-params">,
      duration: </span></span><span class="hljs-number"><span class="hljs-function"><span class="hljs-params"><span class="hljs-number">5000</span></span></span></span><span class="hljs-function"><span class="hljs-params">
    })

    await </span></span><span class="hljs-keyword"><span class="hljs-function"><span class="hljs-params"><span class="hljs-keyword">this</span></span></span></span><span class="hljs-function"><span class="hljs-params">.checkPermissions()
    </span></span><span class="hljs-keyword"><span class="hljs-function"><span class="hljs-params"><span class="hljs-keyword">this</span></span></span></span><span class="hljs-function"><span class="hljs-params">.requestPermissions()

  })</span></span></span><span class="hljs-function">
}

}

}

// 校验应用是否被授予定位权限,可以通过调用checkAccessToken()方法来校验当前是否已经授权。 async checkPermissions(): Promise<boolean> { const permissions: Array<Permissions> = [‘ohos.permission.LOCATION’, ‘ohos.permission.APPROXIMATELY_LOCATION’]; for (let permission of permissions) { let grantStatus = await this.checkAccessToken(permission); if (grantStatus === abilityAccessCtrl.GrantStatus.PERMISSION_GRANTED) { // 启用我的位置图层,mapController为地图操作类对象,获取方式详见地图呈现章节 this.ctrl?.setMyLocationEnabled(true); // 启用我的位置按钮 this.ctrl?.setMyLocationControlsEnabled(true); return true; } } return false; }

// 如果没有被授予定位权限,动态向用户申请授权 requestPermissions(): void { let atManager = abilityAccessCtrl.createAtManager(); atManager.requestPermissionsFromUser(getContext() as common.UIAbilityContext, [‘ohos.permission.LOCATION’, ‘ohos.permission.APPROXIMATELY_LOCATION’]) .then((data: PermissionRequestResult) => { // 启用我的位置图层 this.ctrl?.setMyLocationEnabled(true); }) .catch((err: BusinessError) => { console.error(</span></span><span class="javascript"><span class="hljs-function"><span class="hljs-params"><span class="javascript">Failed to request permissions from user. Code is ${err.code}, message is ${err.message}</span></span></span></span><span class="hljs-function"><span class="hljs-params">); }) }

async checkAccessToken(permission: Permissions): Promise<abilityAccessCtrl.GrantStatus> { let atManager: abilityAccessCtrl.AtManager = abilityAccessCtrl.createAtManager(); let grantStatus: abilityAccessCtrl.GrantStatus = abilityAccessCtrl.GrantStatus.PERMISSION_DENIED;

// 获取应用程序的accessTokenID let tokenId: number = 0; let bundleInfo: bundleManager.BundleInfo = await bundleManager.getBundleInfoForSelf(bundleManager.BundleFlag.GET_BUNDLE_INFO_WITH_APPLICATION); console.info(‘Succeeded in getting Bundle.’); let appInfo: bundleManager.ApplicationInfo = bundleInfo.appInfo; tokenId = appInfo.accessTokenId;

// 校验应用是否被授予权限 grantStatus = await atManager.checkAccessToken(tokenId, permission); console.info(‘Succeeded in checking access token.’); return grantStatus; }

build() { Row() { MapComponent({mapOptions: this.options,mapCallback: this.callback}) .width(‘100%’) .height(‘100%’) } .width(‘100%’) .height(‘100%’) } <button style="position: absolute; padding: 4px 8px 0px; cursor: pointer; top: 4px; right: 8px; font-size: 14px;">复制</button>

}

```

</markdown>

关于HarmonyOS 鸿蒙Next生态下的Map Kit地图服务:功能、应用场景及开发者指南的问题,您也可以访问:https://www.itying.com/category-93-b0.html 联系官网客服。
回到顶部