1# 拉起导航类应用(startAbilityByType)
2
3
4本章节介绍如何拉起导航类应用扩展面板。
5
6## 导航类应用扩展面板参数说明
7
8startAbilityByType接口中type字段为navigation,支持路线规划、导航、位置搜索三种意图场景,对应的wantParam参数如下:
9
10> **说明:**
11> 本文中的经纬度均采用GCJ-02坐标系统。
12
13- 路线规划场景
14
15    | 参数名               | 类型                   | 必填 | 说明                                                 |
16    | -------------------- | ---------------------- | ---- | ---------------------------------------------------- |
17    | sceneType            | number                 | 否   | 意图场景,表明本次请求对应的操作意图。默认为1,路线规划场景填1或不填                   |
18    | originName           | string                 | 否   | 起点名称                                             |
19    | originLatitude       | number                 | 否   | 起点纬度                                             |
20    | originLongitude      | number                 | 否   | 起点经度                                             |
21    | originPoiIds         | Record<number, string> | 否   | 起点POI ID列表,当前仅支持传入花瓣地图和高德地图的POI ID|
22    | destinationName      | string                 | 否   | 终点名称                                             |
23    | destinationLatitude  | number                 | 是   | 终点纬度                                             |
24    | destinationLongitude | number                 | 是   | 终点经度                                             |
25    | destinationPoiIds    | Record<number, string> | 否   | 终点POI ID列表,当前仅支持传入花瓣地图和高德地图的POI ID|
26    | vehicleType          | number                 | 否   | 交通出行工具,取值:0-驾车,1-步行,2-骑行,3-公交; |
27
28- 导航场景
29
30    | 参数名               | 类型                   | 必填 | 说明              |
31    | -------------------- | ---------------------- | ---- | ----------------- |
32    | sceneType            | number                 | 是   | 意图场景,表明本次请求对应的操作意图。导航场景填2 |
33    | destinationName      | string                 | 否   | 终点名称          |
34    | destinationLatitude  | number                 | 是   | 终点纬度          |
35    | destinationLongitude | number                 | 是   | 终点经度          |
36    | destinationPoiIds    | Record<number, string> | 否   | 终点POI ID列表,当前仅支持传入花瓣地图和高德地图的POI ID|
37
38- 位置搜索场景
39
40    | 参数名          | 类型   | 必填 | 说明                  |
41    | --------------- | ------ | ---- | --------------------- |
42    | sceneType       | number | 是   | 意图场景,表明本次请求对应的操作意图。位置搜索场景填3 |
43    | destinationName | string | 是   | 地点名称              |
44
45
46## 拉起方开发步骤
47
481. 导入相关模块。
49    ```ts
50    import { common } from '@kit.AbilityKit';
51    ```
522. 构造接口参数并调用startAbilityByType接口。
53
54   终点POI ID列表(destinationPoiIds)和起点POI ID列表(originPoiIds)需开发者自行从各地图系统中获取,并按照对应关系传参。
55
56
57    ```ts
58    let context = getContext(this) as common.UIAbilityContext;
59    let wantParam: Record<string, Object> = {
60      'sceneType': 1,
61      'destinationLatitude': 32.060844,
62      'destinationLongitude': 118.78315,
63      'destinationName': 'xx市xx路xx号',
64      'destinationPoiIds': {
65          1: '1111',  // key为1代表花瓣地图,value需为花瓣地图POI
66          2: '2222'   // key为2代表高德地图,value需为高德地图POI
67      } as Record<number, string>,
68      'originName': 'xx市xx公园',
69      'originLatitude': 31.060844,
70      'originLongitude': 120.78315,
71      'originPoiIds': {
72          1: '3333',  // key为1代表花瓣地图,value需为花瓣地图POI
73          2: '4444'   // key为2代表高德地图,value需为高德地图POI
74      } as Record<number, string>,
75      'vehicleType': 0
76    };
77    let abilityStartCallback: common.AbilityStartCallback = {
78      onError: (code: number, name: string, message: string) => {
79        console.log(`onError code ${code} name: ${name} message: ${message}`);
80      },
81      onResult: (result)=>{
82        console.log(`onResult result: ${JSON.stringify(result)}`);
83      }
84    }
85
86    context.startAbilityByType("navigation", wantParam, abilityStartCallback,
87        (err) => {
88            if (err) {
89                console.error(`startAbilityByType fail, err: ${JSON.stringify(err)}`);
90            } else {
91                console.log(`success`);
92            }
93    });
94    ```
95    效果示例图:
96
97    ![效果示例图](./figures/start-navigation-panel.png)
98
99## 目标方开发步骤
100
1011. 在module.json5中配置[uris](../quick-start/module-configuration-file.md#skills标签),步骤如下:
102    1. 设置linkFeature属性以声明当前应用支持的特性功能,从而系统可以从设备已安装应用中找到当前支持该特性的应用,取值范围如下:
103        | 取值           | 含义                         |
104        | -------------- | ---------------------------- |
105        | Navigation     | 声明应用支持导航功能 		|
106        | RoutePlan      | 声明应用支持路线规划功能		|
107        | PlaceSearch    | 声明应用支持位置搜索功能     |
108    2. 设置scheme、host、port、path/pathStartWith属性,与Want中URI相匹配,以便区分不同功能。
109    ```json
110    {
111      "abilities": [
112          {
113          "skills": [
114              {
115              "uris": [
116                  {
117                  "scheme": "maps", // 这里仅示意,应用需确保这里声明的的uri能被外部正常拉起
118                  "host": "navigation",
119                  "path": "",
120                  "linkFeature": "Navigation" // 声明应用支持导航功能
121                  },
122                  {
123                  "scheme": "maps", // 这里仅示意,应用需确保这里声明的的uri能被外部正常拉起
124                  "host": "routePlan",
125                  "path": "",
126                  "linkFeature": "RoutePlan" // 声明应用支持路线规划功能
127                  },
128                  {
129                  "scheme": "maps", // 这里仅示意,应用需确保这里声明的的uri能被外部正常拉起
130                  "host": "search",
131                  "path": "",
132                  "linkFeature": "PlaceSearch" // 声明应用支持位置搜索功能
133                  }
134              ]
135              }
136          ]
137          }
138      ]
139    }
140    ```
141
1422. 解析参数并做对应处理。
143
144    ```ts
145    UIAbility.onCreate(want: Want, launchParam: AbilityConstant.LaunchParam): void
146    ```
147
148    在参数**want.uri**中会携带目标方配置的linkFeature对应的uri。
149
150    在参数**want.parameters**中会携带Caller方传入的参数,不同场景参数如下所示。
151
152    - 路线规划场景
153
154        | 参数名               | 类型   | 必填 | 说明                                                 |
155        | -------------------- | ------ | ---- | ---------------------------------------------------- |
156        | originName           | string | 否   | 起点名称                                             |
157        | originLatitude       | number | 否   | 起点纬度                                             |
158        | originLongitude      | number | 否   | 起点经度                                             |
159        | originPoiId          | string | 否   | 起点POI ID,当前仅支持花瓣地图和高德地图获取此参数      |
160        | destinationName      | string | 否   | 终点名称                                             |
161        | destinationLatitude  | number | 是   | 终点纬度                                             |
162        | destinationLongitude | number | 是   | 终点经度                                             |
163        | destinationPoiId     | string | 否   | 终点POI ID,当前仅支持花瓣地图和高德地图获取此参数      |
164        | vehicleType          | number | 否   | 交通出行工具,取值:0-驾车,1-步行,2-骑行,3-公交; |
165
166    - 导航场景
167
168        | 参数名               | 类型   | 必填 | 说明       |
169        | -------------------- | ------ | ---- | ---------- |
170        | destinationName      | string | 否   | 终点名称   |
171        | destinationLatitude  | number | 是   | 终点纬度   |
172        | destinationLongitude | number | 是   | 终点经度   |
173        | destinationPoiId     | string | 否   | 终点POI ID,当前仅支持花瓣地图和高德地图获取此参数|
174
175    - 位置搜索场景
176
177        | 参数名          | 类型   | 必填 | 说明     |
178        | --------------- | ------ | ---- | -------- |
179        | destinationName | string | 是   | 地点名称 |
180
181    应用可根据[linkFeature](../quick-start/module-configuration-file.md#skills标签)中定义的特性功能,比如路线规划、导航和位置搜索,结合接收到的uri和参数开发不同的样式页面。
182
183**完整示例:**
184
185```ts
186import { AbilityConstant, UIAbility, Want } from '@kit.AbilityKit';
187import { hilog } from '@kit.PerformanceAnalysisKit';
188import { window } from '@kit.ArkUI';
189
190const TAG = 'EntryAbility'
191
192export default class EntryAbility extends UIAbility {
193    windowStage: window.WindowStage | null = null;
194
195    uri?: string;
196    destinationLatitude?: number;
197    destinationLongitude?: number;
198    destinationName?: string;
199    originName?: string;
200    originLatitude?: number;
201    originLongitude?: number;
202    vehicleType?: number;
203    destinationPoiId?: string;
204    originPoiId?: string;
205
206    onCreate(want: Want, launchParam: AbilityConstant.LaunchParam): void {
207        hilog.info(0x0000, TAG, `onCreate, want=${JSON.stringify(want)}`);
208        super.onCreate(want, launchParam);
209        this.parseWant(want);
210    }
211
212    onNewWant(want: Want, launchParam: AbilityConstant.LaunchParam): void {
213        hilog.info(0x0000, TAG, `onNewWant, want=${JSON.stringify(want)}`);
214        super.onNewWant(want, launchParam);
215        this.parseWant(want);
216        if (!this.windowStage) {
217            hilog.error(0x0000, TAG, 'windowStage is null');
218            this.context.terminateSelf();
219            return;
220        }
221        this.loadPage(this.windowStage);
222    }
223
224    private parseWant(want: Want): void {
225        this.uri = want.uri as string | undefined;
226        this.destinationLatitude = want.parameters?.destinationLatitude as number | undefined;
227        this.destinationLongitude = want.parameters?.destinationLongitude as number | undefined;
228        this.destinationName = want.parameters?.destinationName as string | undefined;
229        this.originName = want.parameters?.originName as string | undefined;
230        this.originLatitude = want.parameters?.originLatitude as number | undefined;
231        this.originLongitude = want.parameters?.originLongitude as number | undefined;
232        this.vehicleType = want.parameters?.vehicleType as number | undefined;
233        this.destinationPoiId = want.parameters?.destinationPoiId as string | undefined;
234        this.originPoiId = want.parameters?.originPoiId as string | undefined;
235    }
236
237    private loadPage(windowStage: window.WindowStage): void {
238        hilog.info(0x0000, TAG, `loadPage, uri=${this.uri}`);
239        if (this.uri === 'maps://navigation') {
240            // 构建导航场景参数
241            const storage: LocalStorage = new LocalStorage({
242                "destinationLatitude": this.destinationLatitude,
243                "destinationLongitude": this.destinationLongitude,
244                "destinationPoiId": this.destinationPoiId
245            } as Record<string, Object>);
246            // 拉起导航页面
247            windowStage.loadContent('pages/NavigationPage', storage)
248        } else if (this.uri === 'maps://routePlan') {
249            // 构建路径规划场景参数
250            const storage: LocalStorage = new LocalStorage({
251                "destinationLatitude": this.destinationLatitude,
252                "destinationLongitude": this.destinationLongitude,
253                "destinationName": this.destinationName,
254                "originName": this.originName,
255                "originLatitude": this.originLatitude,
256                "originLongitude": this.originLongitude,
257                "vehicleType": this.vehicleType,
258                "destinationPoiId": this.destinationPoiId,
259                "originPoiId": this.originPoiId
260            } as Record<string, Object>);
261            // 拉起路径规划页面
262            windowStage.loadContent('pages/RoutePlanPage', storage)
263        }  else if (this.uri === 'maps://search') {
264            // 构建位置搜索场景参数
265            const storage: LocalStorage = new LocalStorage({
266                "destinationName": this.destinationName
267            } as Record<string, Object>);
268            // 拉起位置搜索页面
269            windowStage.loadContent('pages/PlaceSearchPage', storage)
270        } else {
271            // 默认拉起首页
272            windowStage.loadContent('pages/Index', (err) => {
273                if (err.code) {
274                    hilog.error(0x0000, TAG, 'Failed to load the content. Cause: %{public}s',
275                        JSON.stringify(err) ?? '');
276                    return;
277                }
278                hilog.info(0x0000, TAG, 'Succeeded in loading the content.');
279            });
280        }
281    }
282
283    onDestroy(): void {
284        hilog.info(0x0000, TAG, `onDestroy`);
285    }
286
287    onWindowStageCreate(windowStage: window.WindowStage): void {
288        hilog.info(0x0000, TAG, `onWindowStageCreate`);
289        this.windowStage = windowStage;
290        this.loadPage(this.windowStage);
291    }
292
293    onWindowStageDestroy(): void {
294        hilog.info(0x0000, TAG, '%{public}s', 'Ability onWindowStageDestroy');
295    }
296
297    onForeground(): void {
298        hilog.info(0x0000, TAG, '%{public}s', 'Ability onForeground');
299    }
300
301    onBackground(): void {
302        hilog.info(0x0000, TAG, '%{public}s', 'Ability onBackground');
303    }
304}
305```