Android教程網
  1. 首頁
  2. Android 技術
  3. Android 手機
  4. Android 系統教程
  5. Android 游戲
 Android教程網 >> Android技術 >> 關於Android編程 >> Android 快速掌握高德地圖SDK(內含實踐項目)

Android 快速掌握高德地圖SDK(內含實踐項目)

編輯:關於Android編程

上周學習了高德地圖和極光推送的SDK,需要在項目中用到,不過學習起來還是費了一番功夫去看文檔和Demo代碼的。(不得不吐槽部分文檔真的無厘頭,只有簡單的實例程序注釋都沒有,上下文還不對接,真是醉了),所以打算把最直白的步驟寫在博客中,也希望能幫到還不會用這兩種SDK的小伙伴們,少走彎路,提高工作效率。

 

本文主要介紹高德地圖SDK的使用步驟:

包括從獲取Key,到導包,到布局文件,以及編碼實現。

還有兩個最常用的功能:

實現定位自身。

根據地名或者坐標實現搜索定位並顯示小藍點。

一、獲取高德Key:

進入高德控制台,點擊創建應用,輸入應用名稱和應用類型。

\

應用創建完成後,點擊添加key開始添加新key:

\

SHA1碼的獲取方式有兩種:

1、Eclipse可以直接從Preferances -> Android -> Build查看當前應用的SHA1值。

2、AndroidStudio用戶有兩種方式,第一種通過命令行語句獲得,不過這樣子還要簽名要費一番周折,第二種方式最簡單直接用一個方法輸出當前應用的SHA1值,復制下來就可以了,方法如下(高德文檔提供):

 

public static String sHA1(Context context) {
    try {
        PackageInfo info = context.getPackageManager().getPackageInfo(
                context.getPackageName(), PackageManager.GET_SIGNATURES);
        byte[] cert = info.signatures[0].toByteArray();
        MessageDigest md = MessageDigest.getInstance("SHA1");
        byte[] publicKey = md.digest(cert);
        StringBuffer hexString = new StringBuffer();
        for (int i = 0; i < publicKey.length; i++) {
            String appendString = Integer.toHexString(0xFF & publicKey[i])
                    .toUpperCase(Locale.US);
            if (appendString.length() == 1)
                hexString.append("0");
            hexString.append(appendString);
            hexString.append(":");
        }
        String result = hexString.toString();
        Log.d("xiaojingyu", result);
        return result.substring(0, result.length() - 1);
    } catch (PackageManager.NameNotFoundException e) {
        e.printStackTrace();
    } catch (NoSuchAlgorithmException e) {
        e.printStackTrace();
    }
    return null;
}
之後提交,就會得到一串類似於38bcab8bxxxxxx5bed57ba835e1的字符,這就是我們開發所需要的key了。

 

 

二、導包:

eclipse就不說了,直接把包放到libs裡就可以了。

AndroidStudio復雜一點,但也就是放到libs裡再add 到library就行了。

如下幾個是需要用到的包:

\

以及包下載地址


三、獲取權限:

需要的權限都要添加進AndroidMainfest.xml文件中:

 
















 

 

四、編碼實現:

首先是布局文件:

設置高德sdk指定的MapView:

 

        
        

於是開始代碼的編寫。既然布局文件中用到了MapView,代碼中肯定還是要初始化的:

 

 

MapView mMapView = null;
那這個MapView的作用是什麼呢?讀完代碼(文檔並不會告訴你)我們可以發現它是地圖的View,需要實現地圖的生命周期管理:

 

 

        mMapView = (MapView) v.findViewById(R.id.map);
        //在activity執行onCreate時執行mMapView.onCreate(savedInstanceState),實現地圖生命周期管理
        mMapView.onCreate(savedInstanceState);
當然起到控制作用的還有一個關鍵類AMap,起到對地圖的一些基本管理以及控制接口作用,我們可以在初始化的時候進行如下操作來初始化amap實例:

 

 

        if (aMap == null) {
            aMap = mMapView.getMap();
            aMap.moveCamera(CameraUpdateFactory.zoomTo(0)); //設置縮放為0,則一進來就顯示整個中國大陸
            aMap.setLocationSource(this);// 設置定位監聽
            aMap.getUiSettings().setMyLocationButtonEnabled(true);// 設置默認定位按鈕是否顯示
            aMap.setMyLocationEnabled(true);// 設置為true表示顯示定位層並可觸發定位,false表示隱藏定位層並不可觸發定位,默認是false
            // 設置定位的類型為定位模式 ,可以由定位、跟隨或地圖根據面向方向旋轉幾種
            aMap.setMyLocationType(AMap.LOCATION_TYPE_LOCATE);
        }

 

 

實現當前位置系統小藍點:

我們可以用當前Activity實現AMap定位監聽AMapLocationListener,並重寫它的定位方法:

 

    @Override
    public void onLocationChanged(AMapLocation amapLocation) {
        if (mListener != null && amapLocation != null) {
            if (amapLocation != null
                    && amapLocation.getErrorCode() == 0) {
                mListener.onLocationChanged(amapLocation);// 顯示系統小藍點
            } else {
                String errText = "定位失敗," + amapLocation.getErrorCode() + ": " + amapLocation.getErrorInfo();
                Log.e("AmapErr", errText);
            }
        }
    }
這裡還要用到一個位置改變監聽:OnLocationChangedListener,通過它的方法onLocationChanged(amaplocation)來實現地圖上位置的改變!

 

 

實現響應地理編碼(輸入地名定位到具體位置):

可以看到在Amap的初始化的代碼中需要設置定位監聽,所以需要當前Activity實現LocationSource接口,並重寫激活定位以及停止定位兩個接口方法:

 

    /**
     * 激活定位
     */
    @Override
    public void activate(OnLocationChangedListener listener) {
        Log.d("xiaojingyu", "activate");
        mListener = listener;
        if (mLocationClient == null) {
            mLocationClient = new AMapLocationClient(getActivity());
            mLocationOption = new AMapLocationClientOption();
            //設置定位監聽
            mLocationClient.setLocationListener(this);
            //設置為高精度定位模式
            mLocationOption.setLocationMode(AMapLocationClientOption.AMapLocationMode.Hight_Accuracy);
            //設置定位參數
            mLocationClient.setLocationOption(mLocationOption);
            // 此方法為每隔固定時間會發起一次定位請求,為了減少電量消耗或網絡流量消耗,
            // 注意設置合適的定位時間的間隔(最小間隔支持為2000ms),並且在合適時間調用stopLocation()方法來取消定位請求
            // 在定位結束後,在合適的生命周期調用onDestroy()方法
            // 在單次定位情況下,定位無論成功與否,都無需調用stopLocation()方法移除請求,定位sdk內部會移除
            mLocationClient.startLocation();
        }
    }

    /**
     * 停止定位
     */
    @Override
    public void deactivate() {
        Log.d("xiaojingyu", "deactivate");
        mListener = null;
        if (mLocationClient != null) {
            mLocationClient.stopLocation();
            mLocationClient.onDestroy();
        }
        mLocationClient = null;
    }
這裡需要用到一個定位的Client對象,以及一個Option位置對象

 

記得申明:

public AMapLocationClient mLocationClient = null;
public AMapLocationClientOption mLocationOption = null;

 

 

接下來我們需要申明並初始化兩個搜索組件:

 

//搜索組件
private GeocodeSearch geocoderSearch;
private Marker geoMarker;

都需要在onCreate之後就進行初始化:

 

 

geocoderSearch = new GeocodeSearch(getActivity());
        geocoderSearch.setOnGeocodeSearchListener(this);

            geoMarker = aMap.addMarker(new MarkerOptions().anchor(0.5f, 0.5f)
                    .icon(BitmapDescriptorFactory
                            .defaultMarker(BitmapDescriptorFactory.HUE_BLUE)));
其中geoMarker是用來顯示定位成功之後的小藍點。
接下來我們就可以寫具體的相應地理編碼方法了:

 

 

    /**
     * 響應地理編碼
     */
    public void getLatlon(final String name) {
        //showDialog();
        GeocodeQuery query = new GeocodeQuery(name, "0086");// 第一個參數表示地址,第二個參數表示查詢城市,中文或者中文全拼,citycode、adcode,
        geocoderSearch.getFromLocationNameAsyn(query);// 設置同步地理編碼請求
    }
其中第二個參數我設置成0086是中國的區號,這樣可以實現全國范圍內查找。比如我只設置成長沙的區號0731,那麼我只能輸入長沙的地名進行查找,再查比如岳陽是查不到的。

 

之後會回調geocoderSearch的監聽方法實現定位:

 

    @Override
    public void onGeocodeSearched(GeocodeResult result, int rCode) {
        //dismissDialog();

        if (rCode == 1000) {
            if (result != null && result.getGeocodeAddressList() != null
                    && result.getGeocodeAddressList().size() > 0) {
                GeocodeAddress address = result.getGeocodeAddressList().get(0);
                aMap.animateCamera(CameraUpdateFactory.newLatLngZoom(
                        AMapUtil.convertToLatLng(address.getLatLonPoint()), 15));
                geoMarker.setPosition(AMapUtil.convertToLatLng(address
                        .getLatLonPoint()));
                addressName = "經緯度值:" + address.getLatLonPoint() + "\n位置描述:"
                        + address.getFormatAddress();
                //   ToastUtil.show(getActivity(), addressName);
            } else {
                ToastUtil.show(getActivity(), "沒有查詢到結果~!");
            }
        } else {
            ToastUtil.showerror(getActivity(), rCode);
        }
    }

所謂的相應逆地理編碼其實就是傳入坐標值然後實現定位,跟上文中的相應地理編碼異曲同工,這裡就不再實現一遍了。

 

用到的功能大概就是這些,如果還需要其他的功能可以參考高德SDK官方文檔:
http://lbs.amap.com/api/android-location-sdk/guide/android-location/getlocation/

最後是我最後實現的效果動圖:

\

 

因為涉及項目相關,所以不能把全部源碼貼上來了。

有問題的朋友在評論區留言,我會一一解答。




*************************分隔線*********************

應評論區朋友的要求,在這裡貼上響應逆地理編碼的代碼:

 

    /**
     * 響應逆地理編碼
     */
    public void getAddress(final LatLonPoint latLonPoint) {
        showDialog();
        RegeocodeQuery query = new RegeocodeQuery(latLonPoint, 200,
                GeocodeSearch.AMAP);// 第一個參數表示一個Latlng,第二參數表示范圍多少米,第三個參數表示是火系坐標系還是GPS原生坐標系
        geocoderSearch.getFromLocationAsyn(query);// 設置同步逆地理編碼請求
    }
	/**
	 * 逆地理編碼回調
	 */
	@Override
	public void onRegeocodeSearched(RegeocodeResult result, int rCode) {
		dismissDialog();
		if (rCode == 1000) {
			if (result != null && result.getRegeocodeAddress() != null
					&& result.getRegeocodeAddress().getFormatAddress() != null) {
				addressName = result.getRegeocodeAddress().getFormatAddress()
						+ "附近";
				aMap.animateCamera(CameraUpdateFactory.newLatLngZoom(
						AMapUtil.convertToLatLng(latLonPoint), 15));
				regeoMarker.setPosition(AMapUtil.convertToLatLng(latLonPoint));
				ToastUtil.show(GeocoderActivity.this, addressName);
			} else {
				ToastUtil.show(GeocoderActivity.this, R.string.no_result);
			}
		} else {
			ToastUtil.showerror(this, rCode);
		}
	}

使用方式為在getAddress(LatLonPoint)中傳入需要定位的坐標系,LatLonPoint類是包含在Jar包中的,具體使用方法可以在代碼裡直接ctrl+1查看。
  1. 上一頁:
  2. 下一頁:
熱門文章
閱讀排行版
Copyright © Android教程網 All Rights Reserved