# 定位服务 (HMS)
## 业务介绍
定位服务(Location Kit)采用卫星导航系统(Global Navigation Satellite System,以下简称GNSS)、Wi-Fi、基站等多途径的混合定位模式进行定位,赋予您的应用快速、精准地获取用户位置信息的能力,构建全球定位服务能力,助力您发展全球业务。当前定位服务的主要能力包含三个部分:融合定位、活动识别和地理围栏,您可以根据自己的需求,调用相应的能力。
- 融合定位:结合GNSS、Wi-Fi和基站位置数据,为您提供一套简单易用的API,方便您快速获取设备位置信息。
- 活动识别:通过加速度传感器、蜂窝网络信息、磁力计识别用户运动状态,便于您通过了解用户行为来调整您的应用。
- 地理围栏:您可通过API设置感兴趣的位置区域,在指定操作(如离开、进入、驻留)发生时,即可及时收到一个通知。
### 场景介绍
#### 融合定位
如果您的应用需要请求设备位置信息,首先您需要为应用申请位置权限,然后调用HMS Core的请求位置更新方法([requestLocationUpdates](https://developer.huawei.com/consumer/cn/doc/development/HMSCore-References-V5/fusedlocationproviderclient-0000001050746169-V5#ZH-CN_TOPIC_0000001050746169__section1210118391289)),设置不同的请求([LocationRequest](https://developer.huawei.com/consumer/cn/doc/development/HMSCore-References-V5/locationrequest-0000001050986189-V5))参数,根据您的需要指定定位方式,获取持续的位置信息回调。如果您获取位置信息后,想取消位置信息回调,可以调用移除位置更新方法([removeLocationUpdates](https://developer.huawei.com/consumer/cn/doc/development/HMSCore-References-V5/fusedlocationproviderclient-0000001050746169-V5#ZH-CN_TOPIC_0000001050746169__section14923192365816)),达到取消回调的目的。
说明:
融合定位返回的位置信息使用WGS-84坐标系。
#### 活动识别
如果您的应用需要获取设备的运动状态,例如:步行、跑步、骑自行车等。可以通过以下两种方式获取设备的运动状态:
- 方式一:通过调用活动状态识别更新方法([createActivityIdentificationUpdates](https://developer.huawei.com/consumer/cn/doc/development/HMSCore-References-V5/activityidentificationservice-0000001050986183-V5#ZH-CN_TOPIC_0000001050986183__section177364246397))主动获取当前设备的运动状态。您可以设置检测的时间间隔,以毫秒为单位,检测间隔时间越长,活动检测越少,检测间隔时间越短,活动检测越频繁;调用[deleteActivityIdentificationUpdates](https://developer.huawei.com/consumer/cn/doc/development/HMSCore-References-V5/activityidentificationservice-0000001050986183-V5#ZH-CN_TOPIC_0000001050986183__section18411141614334)方法即可移除活动识别更新。
- 方式二:通过调用活动状态转换方法([createActivityConversionUpdates](https://developer.huawei.com/consumer/cn/doc/development/HMSCore-References-V5/activityidentificationservice-0000001050986183-V5#ZH-CN_TOPIC_0000001050986183__section461610311343))监听当前设备的活动状态转换,监听的时间亮屏是5秒,灭屏是200秒。您可以选定需要监听的运动状态,点击[Constant-values](https://developer.huawei.com/consumer/cn/doc/development/HMSCore-References-V5/constant-values-0000001050746179-V5#ZH-CN_TOPIC_0000001050746179__section1569121418414)查看所有的运动状态;调用[deleteActivityConversionUpdates](https://developer.huawei.com/consumer/cn/doc/development/HMSCore-References-V5/activityidentificationservice-0000001050986183-V5#ZH-CN_TOPIC_0000001050986183__section17434718321)方法即可移除监听。
#### 地理围栏
如果您对某些地点比较关注,您可以根据关注地点的位置,创建地理围栏[createGeofenceList](https://developer.huawei.com/consumer/cn/doc/development/HMSCore-References-V5/geofenceservice-0000001050986187-V5#ZH-CN_TOPIC_0000001050986187__section9254532817),地理围栏可以感知当前设备所在位置和您的关注目标之间的距离,当用户进入围栏区域时,会向应用发起通知。同时,您可以检测用户在围栏内的停留时间,当用户在围栏内停留一段时间之后,再发起通知。
地理围栏同时支持页面操作,通过基于地图的拖拽和参数填写创建地理围栏,详情参见[服务端开发](https://developer.huawei.com/consumer/cn/doc/development/HMSCore-Guides-V5/server-dev-0000001050170474-V5)。
## Unity项目集成设置
### 注册认证
在开始之前,首先您需要创建华为开发者账号,项目,以及App。请参考[华为HMS文档](https://developer.huawei.com/consumer/cn/doc/development/HMS-Guides/Preparations)
![Images/hms/Step1.png](Images/hms/Step1.png)
![Images/hms/Preparation.png](Images/hms/Preparation.png)
我们默认您已经创建并拥有了华为HMS项目,以及对应的App信息
### 创建应用
在您的Unity项目中完成以下构建环境的设置,以便使用华为HMS SDK构建安卓 APK。
![Images/hms/Step2.png](Images/hms/Step2.png)
进入 **Editor -> Build Settings -> Platform -> Andriod**, 点击 **Switch Platform** 切换到安卓平台。
![Images/hms/BuildSettings](Images/hms/BuildSettings.png)
进入 **Player Settings -> Publishing Settings**,勾选以下环境配置项目。
![Images/hms/BuildEnvironment](Images/hms/BuildEnvironment.png)
### 开发准备
按照[华为HMS 集成开发指南介绍](https://developer.huawei.com/consumer/cn/codelab/HMSPreparation/index.html#6),我们仍需要对这些Gradle文件做进一步开发准备的设置。
![Images/hms/Step3.png](Images/hms/Step3.png)
您可以根据[华为HMS Core集成准备](https://developer.huawei.com/consumer/cn/codelab/HMSPreparation/index.html#6)对自己对文件进行配置。您也可以从我们的[示例项目](https://github.com/Unity-Technologies/HMSSDKSample/tree/master/Assets/Plugins/Android)中的具体参数设置,进行参考与对比,完成以下一系列的开发准备配置。
1. 启用并对 `AndroidManifest.xml` 做以下配置
进入 **Edit -> Project Settings -> Player -> Android(icon) -> Publishing Settings -> Build**
启用 **Custom Main Manifest**
当使用“推送服务” 和“定位服务” 的时候,我们需要启用 **AndroidManifest**
如果您的Unity版本低于**2019.2(含)**,上述设置界面中并没有 **AndroidManifest** 选项,但您可以将`AndroidManifest.xml`文件手动放置到`Assets/Plugins/Android` 路径下。
```
```
2. 启用并对project gradle文件添加配置
进入 **Edit -> Project Settings -> Player -> Android(icon) -> Publishing Settings -> Build** ,启用 **Custom Base Gradle Template** 并在文件中添加 AppGallery Connect plugin 和 Maven repository。路径是`Assets/Plugins/Android/baseProjectTemplate.gradle`。
如果您的Unity版本低于**2019.2(含)**,则需要在 MainGradleTemplate.gradle
中添加配置。
```
allprojects {
buildscript {
repositories {**ARTIFACTORYREPOSITORY**
google()
jcenter()
maven { url 'https://developer.huawei.com/repo/' }
}
dependencies {
// If you are changing the Android Gradle Plugin version, make sure it is compatible with the Gradle version preinstalled with Unity
// See which Gradle version is preinstalled with Unity here https://docs.unity3d.com/Manual/android-gradle-overview.html
// See official Gradle and Android Gradle Plugin compatibility table here https://developer.android.com/studio/releases/gradle-plugin#updating-gradle
// To specify a custom Gradle version in Unity, go do "Preferences > External Tools", uncheck "Gradle Installed with Unity (recommended)" and specify a path to a custom Gradle version
classpath 'com.android.tools.build:gradle:3.4.0'
classpath 'com.huawei.agconnect:agcp:1.2.1.301'
**BUILD_SCRIPT_DEPS**
}
}
repositories {**ARTIFACTORYREPOSITORY**
google()
jcenter()
flatDir {
dirs "${project(':unityLibrary').projectDir}/libs"
}
maven { url 'https://developer.huawei.com/repo/' }
}
}
task clean(type: Delete) {
delete rootProject.buildDir
}
```
3. 启用并对app gradle文件添加配置
进入 **Edit -> Project Settings -> Player -> Android(icon) -> Publishing Settings -> Build**,启用 **Custom Launcher Gradle Template** 并在 `launcherTemplate.gradle` 中添加依赖。路径为 `Assets/Plugins/Android/LauncherTemplate.gradle`。
如果您的Unity版本低于**2019.2(含)**, 则需要在 MainGradleTemplate.gradle
中添加配置。
```
dependencies {
implementation project(':unityLibrary')
implementation 'com.huawei.hms:ads-lite:13.4.29.303'
implementation 'com.huawei.hms:ads-consent:3.4.30.301'
implementation 'com.huawei.hms:push:4.0.3.301'
implementation 'com.huawei.hms:hianalytics:5.1.0.300'
implementation 'com.android.support:appcompat-v7:28.0.0'
implementation 'com.huawei.hms:hianalytics:5.0.0.301'
implementation 'com.huawei.agconnect:agconnect-core:1.6.1.300'
implementation 'com.huawei.hms:base:6.2.0.300'
implementation 'com.huawei.hms:hwid:6.1.0.303'
implementation 'com.huawei.hms:game:6.1.0.301'
}
```
4. 使用并对unity library gradle文件进行以下设置
进入 **Edit -> Project Settings -> Player -> Android(icon) -> Publishing Settings -> Build**,启用 **Custom Main Gradle Template** 并在 `mainTemplate.gradle` 中添加依赖。路径为 `Assets/Plugins/Android/mainTemplate.gradle.gradle`。
如果您的Unity版本低于**2019.2(含)**, 则需要在 MainGradleTemplate.gradle
中添加配置。
```
dependencies {
implementation fileTree(dir: 'libs', include: ['*.jar'])
implementation 'com.huawei.hms:hianalytics:5.0.0.301'
implementation 'com.huawei.agconnect:agconnect-core:1.6.1.300'
implementation 'com.huawei.hms:base:6.2.0.300'
implementation 'com.huawei.hms:hwid:6.1.0.303'
implementation 'com.huawei.hms:game:6.1.0.301'
**DEPS**}
```
5. 创建Signature
进入 **Edit -> Project Settings -> Player -> Android(icon) -> Publishing Settings -> Keystore Manager**, 点击 **Keytore... -> create new**
![Images/hms/Keystore.png](Images/hms/Keystore.png)
您需要在打开unity时设定并输入密码,否则将无法构建。无需在 gradle 中添加signature。
6. 签署证书指纹
参照华为[HMS Core集成准备 Step4](https://developer.huawei.com/consumer/cn/codelab/HMSPreparation/index.html#3) 生成SHA256证书指纹
![Images/hms/Fingerprint.png](Images/hms/Fingerprint.png)
参照华为[HMS Core集成准备 Step5](https://developer.huawei.com/consumer/cn/codelab/HMSPreparation/index.html#4)在AppGAllery Connect里添加指纹。
![Images/hms/FingerprintAppGallery.png](Images/hms/FingerprintAppGallery.png)
7. 设置package name,及其他设置
进入 **Edit -> Project Settings -> Player**设置package name。
package name格式为 `com.${Company Name}.${Product Name}`
同时也可以在此步骤完成其余的所需设置,比如您的应用版本号、应用的图标、设置显示的分辨率等。
![Images/hms/PackageName.png](Images/hms/PackageName.png)
8. `Agconnect-services.json`
我们还需要从华为开发者账号内下载这个json文件,加入所需信息后,放到 `Assets/Plugins/Android` 路径下。
从华为开发者账号内下载此json 文件并在其中加以下信息。同样的,您可以在我们的[示例项目文件](https://github.com/Unity-Technologies/HMSSDKSample/blob/master/Assets/Plugins/Android/agconnect-services.json)中直接参考!
```
"agcgw":{
"backurl":"connect-drcn.dbankcloud.cn",
"url":"connect-drcn.hispace.hicloud.com"
},
```
当我们使用“分析服务”、“推送服务”、或“定位服务”时,必须配置 `agconnect-services.json` 文件。
参考 [链接](https://developer.huawei.com/consumer/cn/doc/development/HMSCore-Guides/android-config-agc-0000001050170137) 以创建`agconnect-services.json`
![Images/hms/AgcConnectServicesJson.png](Images/hms/AgcConnectServicesJson.png)
9. 配置混淆脚本
编译APK前需要配置混淆配置文件,避免混淆HMS Core SDK导致功能异常。([参考文档](https://developer.huawei.com/consumer/cn/doc/development/HMSCore-Guides/config-obfuscation-scripts-0000001188775555))
- 在您的Unity项目里打开混淆配置文件,加入排除HMS Core SDK的混淆配置。
```
-ignorewarnings
-keepattributes *Annotation*
-keepattributes Exceptions
-keepattributes InnerClasses
-keepattributes Signature
-keepattributes SourceFile,LineNumberTable
-keep class com.huawei.hianalytics.**{*;}
-keep class com.huawei.updatesdk.**{*;}
-keep class com.huawei.hms.**{*;}
-keep class * extends com.huawei.hms.core.aidl.IMessageEntity{ *; }
-keep public class com.huawei.location.nlp.network.** {*; }
-keep class com.huawei.wisesecurity.ucs.**{*;}
```
- (可选)当您启用R8资源缩减(项目级“build.gradle”文件中shrinkResources属性为“true”)和严格引用检查(“res/raw/keep.xml”文件中的shrinkMode为“strict”)时,请您配置“keep.xml”文件手动保留layout资源,确保应用正常通过华为应用市场上架审核。
```
```
10. 获取activity
可以用 `Common.GetActivity()`函数来获取activity。
## SDK集成开发
### SDK开发
HMS 套件中共包括4个功能服务,在[示例项目](https://github.com/Unity-Technologies/HMSSDKSample)中都有相应的示例场景。 为了进行测试,您需要通过HMS将其构建到Android移动版上。 确保已创建HMS帐户和项目。 然后,您就可以更改配置并测试不同的功能。
![Images/hms/Step4.png](Images/hms/Step4.png)
我们需要把 `com.android.support:appcompat-v7:28.0.0` 加到 **launcherTemplate** 中
在示例项目中,定位服务对应的场景是: `Assets/HuaweiServiceDemo/Scenes/HmsLocationSampleScene.unity`
对应的代码是: `Assets/HuaweiServiceDemo/demo/test/location/LocationTest.cs`.
我们需要设置接收器
- **LocationBroadcastReceiver**
1. 实现 `IBroadcastReceiver`接口
2. 通过 `BroadcastRegister.CreateLocationReceiver` 方法得到接收器
3. 添加以下代码到 `AndroidManifest.xml` 中:
```
...
...
```
`android:name` 是固定的。
您可以设置 `action android:name` 的值,但这个值应该与 `intent.setAction` 的参数相同。
- **GeoFenceReceiver**
1. 实现 `IBroadcastReceiver` 接口
2. 通过 `BroadcastRegister.CreateGeoFenceReceiver` 方法得到接收器
3. 添加以下代码到 `AndroidManifest.xml` 中
```
...
...
```
`android:name` 是固定的。
您可以设置 `action android:name` 的值,但这个值应该与 `intent.setAction` 的参数相同
### 测试与发布
参考华为 [HMS Core集成流程](https://developer.huawei.com/consumer/cn/doc/start/hitHMSCore) for testing and releasing.
![Images/hms/TestAndRelease.png](Images/hms/TestAndRelease.png)
![Images/hms/TestingReleasing.png](Images/hms/TestingReleasing.png)