初次見面
在國內(nèi),說到集成地圖服務(wù),大多用的是高德和百度地圖提供的相關(guān)接口。自從華為開始做地圖服務(wù)以后(目前華為地圖服務(wù)還不支持中國大陸區(qū)域,但愿不久的將來華為地圖能夠融入我們?nèi)粘I畹姆椒矫婷姘蓗),迅速就有一大批開發(fā)者參與進(jìn)來,其開放平臺也提供了地圖服務(wù)相關(guān)的接口和文檔,那么今天就和華為地圖來一次美麗的邂逅吧??

首先,我們先來打開【華為開發(fā)者平臺-地圖服務(wù)】的部分,可以看到下面內(nèi)容:
業(yè)務(wù)簡介
地圖服務(wù)(Map Kit)給開發(fā)者提供一套地圖開發(fā)調(diào)用的SDK,地圖數(shù)據(jù)覆蓋超過200個國家和地區(qū),支持?jǐn)?shù)十種語言,方便開發(fā)者輕松地在應(yīng)用中集成地圖相關(guān)的功能,全方位提升用戶體驗。
從支持的國家和地區(qū)的數(shù)量來看,華為一開始的目標(biāo)就是針對全球提供服務(wù)的,直接對標(biāo)谷歌地圖,這很華為?。?!
再來看版本更新說明,最近一次的更新在2020年9月18日,距離今天也是剛剛發(fā)布不久,版本號是5.0.2.300,不知不覺已經(jīng)更新到5.x版本了,厲害了!

附上官方GitHub地址:HMS-Core/hms-mapkit-demo-java
集成準(zhǔn)備
不同的地圖服務(wù),它的集成方式肯定是不完全一樣的,那么我們先按照官網(wǎng)的文檔來進(jìn)行集成工作。ok,先來看一下開發(fā)準(zhǔn)備相關(guān)的內(nèi)容吧。
從文檔我們可以看到,一共分為四個部分,分別為:
- 配置AppGallery Connect
- 集成HMS Core SDK
- 配置混淆腳本
- 添加權(quán)限
1. 配置AppGallery Connect
注冊成為開發(fā)者
首先,要使用華為地圖服務(wù)的能力,必須注冊成為開發(fā)者并完成實名認(rèn)證,這一步我之前就已經(jīng)做好了,所以此過程就不贅述了,注冊過程都大同小異很簡單,注冊網(wǎng)址:華為開發(fā)者聯(lián)盟網(wǎng)站
創(chuàng)建應(yīng)用
登錄成功以后開始創(chuàng)建應(yīng)用(先創(chuàng)建項目,再在項目下面創(chuàng)建應(yīng)用),這里我包名注冊為:com.test.hellohuaweimaps,截圖如下:

創(chuàng)建成功以后,信息如下:

接著,我們點擊agconnect-services.json的下載按鈕,下載一個json文件,控油備用??梢韵葋砜聪逻@個文件內(nèi)容是什么,其實就是我們剛才創(chuàng)建項目的一些信息,appid和包名這些之類的,打開如下:
{
"client":{
"cp_id":"260086000054571879",
"product_id":"736430079244623765",
"client_id":"444159260570420352",
"client_secret":"E02F4B50235CFD06F5B1A629B9A4E1FF6E51C5D9712FE9203A4FC3F26DC8CDF1",
"app_id":"102999311",
"package_name":"com.test.hellohuaweimaps",
"api_key":"CgB6e3x9LlZu7CzGeBgFTFlfnN3HEIEkSZSYEudrrDlhlqfQNlQbPOhsy3W/BZbkXpxZDyqqMkdyrtC36iYZ2I31"
},
"configuration_version":"1.0"
}
-
配置簽名證書指紋
那么,為什么要配置這個簽名證書呢,原因很簡單,我們來看官網(wǎng)的描述是這樣的:
簽名證書指紋用于在通過華為HMS Core SDK調(diào)用HMS Core(APK)時,校驗應(yīng)用的真實性。開發(fā)者在使用HMS Core(APK)前必須將簽名證書指紋配置到AppGallery Connect,在配置前需要根據(jù)簽名證書在本地生成簽名證書指紋。
原因就是為了做一個合法檢驗了,為了過濾掉一些未簽名的不法應(yīng)用。OK,那我們先來生成簽名證書指紋,你需要準(zhǔn)備一個簽名文件(keystore或者jks類型的文件),和配置好環(huán)境了的JDK,然后很簡單一個命令就搞定了:
命令:keytool -list -v -keystore <簽名文件路徑>
zhuyongdeMacBook-Pro:~ zhuyong$ keytool -list -v -keystore /Users/zhuyong/Desktop/keystore/hwmapdemo.jks
輸入密鑰庫口令:
密鑰庫類型: jks
密鑰庫提供方: SUN
您的密鑰庫包含 1 個條目
別名: bravejoy
創(chuàng)建日期: 2020-9-4
條目類型: PrivateKeyEntry
證書鏈長度: 1
證書[1]:
所有者: CN=bravejoy
發(fā)布者: CN=bravejoy
序列號: 6c406261
有效期為 Fri Sep 04 20:03:09 CST 2020 至 Tue Aug 29 20:03:09 CST 2045
證書指紋:
MD5: F6:0E:41:C0:01:44:E5:C8:4E:D3:C7:4F:EE:A8:81:17
SHA1: EB:82:61:B1:84:07:C4:F7:CD:A0:56:31:9E:6B:74:A1:17:0E:52:94
SHA256: 76:20:FD:9A:18:DA:AB:B9:51:D7:9B:B8:00:4F:B9:3D:59:CD:86:24:4F:13:A3:70:16:3E:D7:7C:04:3C:D7:1A
簽名算法名稱: SHA256withRSA
主體公共密鑰算法: 2048 位 RSA 密鑰
版本: 3
復(fù)制其中的SHA256數(shù)據(jù),然后粘貼到對應(yīng)位置即可,我這里生成配置如下:

2. 集成HMS Core SDK
-
打開Android Studio,新建項目
ps:注意包名要和上面一致,我這里為:com.test.hellohuaweimaps
新建項目以后,把剛才下載的json文件放至如下位置:

-
配置AGC插件和SDK的Maven倉庫地址
打開項目根目錄build.gradle文件,配置如下:
buildscript {
repositories {
google()
jcenter()
//agconnect插件maven倉地址,必須配置
maven {url 'https://developer.huawei.com/repo/'}
}
dependencies {
classpath 'com.android.tools.build:gradle:3.6.1'
////agconnect插件
classpath 'com.huawei.agconnect:agcp:1.3.1.300'
}
}
allprojects {
repositories {
google()
jcenter()
//maven倉地址,下載地圖sdk
maven {url 'https://developer.huawei.com/repo/'}
}
}
task clean(type: Delete) {
delete rootProject.buildDir
}
-
依賴地圖SDK
打開app目錄下的build.gradle文件,配置如下:
apply plugin: 'com.android.application'
apply plugin: 'com.huawei.agconnect'//agc相關(guān)插件
android {
compileSdkVersion 29
buildToolsVersion "29.0.3"
defaultConfig {
applicationId "com.test.hellohuaweimaps"
minSdkVersion 19
targetSdkVersion 29
versionCode 1
versionName "1.0"
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
}
}
}
dependencies {
implementation fileTree(dir: 'libs', include: ['*.jar'])
implementation 'androidx.appcompat:appcompat:1.2.0'
implementation 'androidx.constraintlayout:constraintlayout:2.0.1'
testImplementation 'junit:junit:4.12'
androidTestImplementation 'androidx.test.ext:junit:1.1.2'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.3.0'
//華為地圖SDK
implementation 'com.huawei.hms:maps:5.0.2.300'
}
- 執(zhí)行sync,同步成功
3. 配置混淆腳本
-ignorewarnings
-keepattributes *Annotation*
-keepattributes Exceptions
-keepattributes InnerClasses
-keepattributes Signature
-keepattributes SourceFile,LineNumberTable
-keep class com.hianalytics.android.**{*;}
-keep class com.huawei.updatesdk.**{*;}
-keep class com.huawei.hms.**{*;}
4. 添加權(quán)限
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
<uses-permission android:name="com.huawei.appmarket.service.commondata.permission.GET_COMMON_DATA"/>
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"/>
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
初次握手
到這里其實我們已經(jīng)做了很多工作了,那么從現(xiàn)在開始我們就要開始真正地使用地圖API了。
-
使用MapView控件
打開activity_main文件,引用MapView控件如下:
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity">
<com.huawei.hms.maps.MapView
android:id="@+id/mapView"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
- 在Activity中聲明并使用
public class MainActivity extends AppCompatActivity implements OnMapReadyCallback {
private MapView mMapView;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mMapView = findViewById(R.id.mapView);
Bundle mapViewBundle = null;
if (savedInstanceState != null) {
mapViewBundle = savedInstanceState.getBundle("MapViewBundleKey");
}
mMapView.onCreate(mapViewBundle);
mMapView.getMapAsync(this);
}
/**
* 當(dāng)?shù)貓D準(zhǔn)備完成以后,會回調(diào)次方法
*
* @param huaweiMap 地圖對象
*/
@Override
public void onMapReady(HuaweiMap huaweiMap) {
}
@Override
protected void onStart() {
super.onStart();
mMapView.onStart();
}
@Override
protected void onResume() {
super.onResume();
mMapView.onResume();
}
@Override
protected void onPause() {
super.onPause();
mMapView.onPause();
}
@Override
protected void onStop() {
super.onStop();
mMapView.onStop();
}
@Override
protected void onDestroy() {
super.onDestroy();
mMapView.onDestroy();
}
@Override
public void onLowMemory() {
super.onLowMemory();
mMapView.onLowMemory();
}
}
-
運行項目
然后看到的效果是這樣的,只有一些網(wǎng)格狀的東西,根本看不到地圖,腦瓜子嗡嗡的:

想一下,我們剛才在官網(wǎng)配置的簽名證書指紋貌似還沒有派上用場,問題肯定是出在這里了,來看一下有沒有報錯的日志信息,從日志里我們可以看到下面這樣一句error日志,告訴我們證書指紋無效,因為我們并沒有對apk進(jìn)行簽名。
HmsMapKit_AuthenticateClient_319: responseBody is returnCode: 010002;
resultInfo : the certificate fingerprint is invalid.
先不配置簽名,我們先來用簽名文件打包一個apk試一下,然后手動安裝運行:

果不其然,地圖出來了哦!??!

備注:使用華為地圖服務(wù)需要在手機(jī)提前安裝HmsCore【華為移動服務(wù)】。
好吧,既然已經(jīng)確定了原因所在,那我們就在gradle里配置一下apk簽名吧,打開app目下的build.gradle文件,在android{}內(nèi)增加如下配置:
signingConfigs {
release {
//將簽名文件放至app根目錄下,和 agconnect-services.json在同一個目錄下
storeFile file("hwmapdemo.jks")
storePassword "123456"
keyAlias "bravejoy"
keyPassword "123456"
v2SigningEnabled true
}
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
signingConfig signingConfigs.release
}
debug {
//此配置是為了debug模式下也能夠?qū)pk進(jìn)行簽名,方便運行調(diào)試。
signingConfig signingConfigs.release
}
}
執(zhí)行Sync,然后卸載手機(jī)app,再次直接點擊運行,地圖成功顯示。
初次互動
既然地圖都已經(jīng)出來了,那就再小小地互動一下吧。
-
移動相機(jī)視角
移動到北京的位置(經(jīng)緯度:39.909736,116.397400) -
添加一個marker,并增加點擊事件
在onMapReady回調(diào)方法中添加以下代碼:
/**
* 當(dāng)?shù)貓D準(zhǔn)備完成以后,會回調(diào)次方法
*
* @param huaweiMap 地圖對象
*/
@Override
public void onMapReady(HuaweiMap huaweiMap) {
//構(gòu)造一個經(jīng)緯度坐標(biāo)對象
LatLng latLng = new LatLng(39.909736, 116.397400);
//移動相機(jī)到指定位置
huaweiMap.animateCamera(CameraUpdateFactory.newLatLngZoom(latLng, 3));
//在地圖上添加Marker
huaweiMap.addMarker(new MarkerOptions()
.position(latLng)
.icon(BitmapDescriptorFactory.defaultMarker())
.title("I'm Beijing")
.snippet("I'm Beijing"));
//添加Marker點擊事件監(jiān)聽器
huaweiMap.setOnMarkerClickListener(new HuaweiMap.OnMarkerClickListener() {
@Override
public boolean onMarkerClick(Marker marker) {
Toast.makeText(MainActivity.this, "This is Beijing", Toast.LENGTH_SHORT).show();
return false;
}
});
}

好了,到這里就算是跟華為地圖真的認(rèn)識了,以后愿她會認(rèn)識更多的開發(fā)者,也希望她會越來越好,成為世界第一?。?!