第一步 AndroidManifest 配置
<uses-permission android:name="android.permission.WAKE_LOCK" /> <!--用于进行网络定位--> <uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"></uses-permission> <!--用于访问GPS定位--> <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"></uses-permission> <!--用于获取运营商信息,用于支持提供运营商信息相关的接口--> <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"></uses-permission> <!--用于访问wifi网络信息,wifi信息会用于进行网络定位--> <uses-permission android:name="android.permission.ACCESS_WIFI_STATE"></uses-permission> <!--用于获取wifi的获取权限,wifi信息会用来进行网络定位--> <uses-permission android:name="android.permission.CHANGE_WIFI_STATE"></uses-permission> <!--用于访问网络,网络定位需要上网--> <uses-permission android:name="android.permission.INTERNET"></uses-permission> <!--用于读取手机当前的状态--> <uses-permission android:name="android.permission.READ_PHONE_STATE"></uses-permission> <!--用于写入缓存数据到扩展存储卡--> <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"></uses-permission> <!--用于申请调用A-GPS模块--> <uses-permission android:name="android.permission.ACCESS_LOCATION_EXTRA_COMMANDS"></uses-permission> <!--用于申请获取蓝牙信息进行室内定位--> <uses-permission android:name="android.permission.BLUETOOTH"></uses-permission> <uses-permission android:name="android.permission.BLUETOOTH_ADMIN"></uses-permission>
<service android:name="com.amap.api.location.APSService"></service> <meta-data android:name="com.amap.api.v2.apikey" android:value="自己的高德Key"> </meta-data> <activity android:name="com.amap.api.navi.AmapRouteActivity" android:theme="@android:style/Theme.NoTitleBar" android:configChanges="orientation|keyboardHidden|screenSize" />
导入依赖
compile 'com.amap.api:navi-3dmap:latest.integration' compile 'com.amap.api:location:latest.integration' compile 'com.google.code.gson:gson:2.2.4'
创建MapUtils类。传入Context;
定位功能方法 getAddress()
导航功能 startNavigation();
加载地图 setMap();
加载地图并且显示出对应位置的覆盖物 setMap();
覆盖物的点击事件 在Activity中调用。
aMap.setOnMarkerClickListener(new AMap.OnMarkerClickListener() { @Override public boolean onMarkerClick(Marker marker) { return true; } });
参数列表如果不懂 就直接crtl+方法名 查看方法注释。
获取APP的SHAI码 当SHAI码错误为7时 调用getSHAICode()方法 查看log日志 复制SHAI码,保存到高德的key中即可。
把以下的代码复制到MapUtils中
注意!!!
请把这个类中第一个成员变量KEY 修改为自己的高德Web端KEY
是WebKey 如果没有请创建一个
看下面这张图片
添加新的key 选择WEB服务即可
import android.content.Context; import android.content.pm.PackageInfo; import android.content.pm.PackageManager; import android.graphics.BitmapFactory; import android.os.Handler; import android.os.Message; import android.util.Log; import android.widget.Toast; import com.amap.api.location.AMapLocation; import com.amap.api.location.AMapLocationClient; import com.amap.api.location.AMapLocationClientOption; import com.amap.api.location.AMapLocationListener; import com.amap.api.maps.AMap; import com.amap.api.maps.model.BitmapDescriptorFactory; import com.amap.api.maps.model.LatLng; import com.amap.api.maps.model.Marker; import com.amap.api.maps.model.MarkerOptions; import com.amap.api.maps.model.MyLocationStyle; import com.amap.api.maps.model.Poi; import com.amap.api.navi.AmapNaviPage; import com.amap.api.navi.AmapNaviParams; import com.amap.api.navi.AmapNaviType; import com.amap.api.navi.INaviInfoCallback; import com.amap.api.navi.model.AMapNaviLocation; import com.google.gson.Gson; import java.io.BufferedReader; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.net.HttpURLConnection; import java.net.MalformedURLException; import java.net.URL; import java.security.MessageDigest; import java.security.NoSuchAlgorithmException; import java.util.List; import java.util.Locale; public class MapUtils { private static final String KEY = "9f7d8208163298f2dc39e70139a4cf6f"; private AMap aMap; private boolean boo = true; private Context context; private AMapLocationClientOption mLocationOption = null; private AMapLocationClient mLocationClient = null; public MapUtils(Context context) { this.context = context; } private Handler mHandler = new Handler() { public void handleMessage(Message msg) { switch (msg.what) { case 1: initHandler(msg); break; } } }; /** * 反义地理编码导航 * @param msg */ private void initHandler(Message msg) { Bean bean = (Bean) msg.obj; try { String[] split = bean.getGeocodes().get(0).getLocation().split(","); double x = Double.parseDouble(split[0]); double y = Double.parseDouble(split[1]); LatLng latLng = new LatLng(y, x); if(boo) { Poi end = new Poi(bean.getGeocodes().get(0).getFormatted_address(), latLng, ""); AmapNaviPage.getInstance().showRouteActivity(context, new AmapNaviParams(null, null, end, AmapNaviType.DRIVER), iNaviInfoCallback); }else { Marker marker = aMap.addMarker(new MarkerOptions() .position(latLng) .visible(true) .icon(BitmapDescriptorFactory.fromBitmap(BitmapFactory .decodeResource(context.getResources(), R.mipmap.ic_launcher))) .draggable(true)); marker.setVisible(true); boo = true; } } catch (Exception a) { Toast.makeText(context, "地址值有误", Toast.LENGTH_SHORT).show(); } } /** * 显示地图 * 传入的参数为(控件.getMap) */ public void setMap(AMap aMap) { MyLocationStyle myLocationStyle = new MyLocationStyle(); aMap.setMyLocationStyle(myLocationStyle); aMap.setMyLocationEnabled(true); myLocationStyle.showMyLocation(true); myLocationStyle.myLocationType(MyLocationStyle.LOCATION_TYPE_LOCATION_ROTATE); } /** * 显示地图 * 传入的参数为(控件.getMap,显示覆盖物的地址) */ public void setMap(AMap aMap,String address) { boo = false; this.aMap = aMap; MyLocationStyle myLocationStyle = new MyLocationStyle(); this.aMap.setMyLocationStyle(myLocationStyle); this.aMap.setMyLocationEnabled(true); myLocationStyle.showMyLocation(true); myLocationStyle.myLocationType(MyLocationStyle.LOCATION_TYPE_LOCATE); startNavigation(address); } /** * 定位功能 * @param getData */ public void getAddress(final GetData getData) { this.getData = getData; //初始化定位 mLocationClient = new AMapLocationClient(context.getApplicationContext()); //设置定位回调监听 mLocationClient.setLocationListener(new AMapLocationListener() { @Override public void onLocationChanged(AMapLocation aMapLocation) { if (aMapLocation != null) { if (aMapLocation.getErrorCode() == 0) { String address = aMapLocation.getAddress(); getData.setData(address); } else { Log.e("错误信息:", "错误代码:" + aMapLocation.getErrorCode() + ", 解决方法:" + aMapLocation.getErrorInfo()); } } } }); mLocationOption = new AMapLocationClientOption(); mLocationOption.setLocationPurpose(AMapLocationClientOption.AMapLocationPurpose.SignIn); if (null != mLocationClient) { mLocationClient.setLocationOption(mLocationOption); //设置场景模式后最好调用一次stop,再调用start以保证场景模式生效 mLocationClient.stopLocation(); mLocationClient.startLocation(); } mLocationOption.setLocationMode(AMapLocationClientOption.AMapLocationMode.Hight_Accuracy); mLocationOption.setOnceLocationLatest(true); mLocationOption.setNeedAddress(true); mLocationOption.setMockEnable(false); mLocationOption.setHttpTimeOut(20000); mLocationOption.setLocationCacheEnable(false); mLocationClient.setLocationOption(mLocationOption); mLocationClient.startLocation(); } /** * 导航功能 * @param address 目的地 */ public void startNavigation(String address) { StringBuffer sb = new StringBuffer(); sb.append("http://restapi.amap.com/v3/geocode/geo?key=" + KEY + "&address=" + address + "&output=JSON"); initData(sb.toString()); } public void startNavigation() { AmapNaviPage.getInstance().showRouteActivity(context, new AmapNaviParams(null), iNaviInfoCallback); } /** * 导航接口 */ INaviInfoCallback iNaviInfoCallback = new INaviInfoCallback() { @Override public void onInitNaviFailure() { } @Override public void onGetNavigationText(String s) { } @Override public void onLocationChange(AMapNaviLocation aMapNaviLocation) { } @Override public void onArriveDestination(boolean b) { } @Override public void onStartNavi(int i) { } @Override public void onCalculateRouteSuccess(int[] ints) { } @Override public void onCalculateRouteFailure(int i) { } @Override public void onStopSpeaking() { } @Override public void onReCalculateRoute(int i) { } @Override public void onExitPage(int i) { } }; /** * 网络请求地理编码 * * @param path */ private void initData(final String path) { new Thread(new Runnable() { @Override public void run() { try { URL url = new URL(path); HttpURLConnection connection = (HttpURLConnection) url.openConnection(); int code = connection.getResponseCode(); if (code == 200) { InputStream inputStream = connection.getInputStream(); BufferedReader reader = new BufferedReader(new InputStreamReader(inputStream, "utf-8")); StringBuffer sb = new StringBuffer(); String str; while ((str = reader.readLine()) != null) { sb.append(str); } Bean bean = new Gson().fromJson(sb.toString(), Bean.class); Message message = new Message(); message.obj = bean; message.what = 1; mHandler.sendMessage(message); } } catch (MalformedURLException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } } }).start(); } /** * 如果报错SHA1不对 错误码为7 就调用这个方法 * 查找log日志对应的SHA1码 生成在高德中 */ public void getSHA1Code(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(":"); } hexString.deleteCharAt(hexString.length() - 1); String result = hexString.toString(); Log.e("-------------------", result); } catch (PackageManager.NameNotFoundException e) { e.printStackTrace(); } catch (NoSuchAlgorithmException e) { e.printStackTrace(); } } public interface GetData { void setData(String address); } private GetData getData; /** * 获取地理编码的实体类 */ static class Bean { /** * status : 1 * info : OK * infocode : 10000 * count : 1 * geocodes : [{"formatted_address":"北京市朝阳区方恒国际中心|A座","province":"北京市","citycode":"010","city":"北京市","district":"朝阳区","township":[],"neighborhood":{"name":[],"type":[]},"building":{"name":[],"type":[]},"adcode":"110105","street":[],"number":[],"location":"116.480724,39.989584","level":"门牌号"}] */ private String status; private String info; private String infocode; private String count; private List<GeocodesBean> geocodes; public String getStatus() { return status; } public void setStatus(String status) { this.status = status; } public String getInfo() { return info; } public void setInfo(String info) { this.info = info; } public String getInfocode() { return infocode; } public void setInfocode(String infocode) { this.infocode = infocode; } public String getCount() { return count; } public void setCount(String count) { this.count = count; } public List<GeocodesBean> getGeocodes() { return geocodes; } public void setGeocodes(List<GeocodesBean> geocodes) { this.geocodes = geocodes; } public static class GeocodesBean { /** * formatted_address : 北京市朝阳区方恒国际中心|A座 * province : 北京市 * citycode : 010 * city : 北京市 * district : 朝阳区 * township : [] * neighborhood : {"name":[],"type":[]} * building : {"name":[],"type":[]} * adcode : 110105 * street : [] * number : [] * location : 116.480724,39.989584 * level : 门牌号 */ private String formatted_address; private String province; private String citycode; private String city; private String district; private NeighborhoodBean neighborhood; private BuildingBean building; private String adcode; private String location; private String level; private List<?> township; private List<?> street; private List<?> number; public String getFormatted_address() { return formatted_address; } public void setFormatted_address(String formatted_address) { this.formatted_address = formatted_address; } public String getProvince() { return province; } public void setProvince(String province) { this.province = province; } public String getCitycode() { return citycode; } public void setCitycode(String citycode) { this.citycode = citycode; } public String getCity() { return city; } public void setCity(String city) { this.city = city; } public String getDistrict() { return district; } public void setDistrict(String district) { this.district = district; } public NeighborhoodBean getNeighborhood() { return neighborhood; } public void setNeighborhood(NeighborhoodBean neighborhood) { this.neighborhood = neighborhood; } public BuildingBean getBuilding() { return building; } public void setBuilding(BuildingBean building) { this.building = building; } public String getAdcode() { return adcode; } public void setAdcode(String adcode) { this.adcode = adcode; } public String getLocation() { return location; } public void setLocation(String location) { this.location = location; } public String getLevel() { return level; } public void setLevel(String level) { this.level = level; } public List<?> getTownship() { return township; } public void setTownship(List<?> township) { this.township = township; } public List<?> getStreet() { return street; } public void setStreet(List<?> street) { this.street = street; } public List<?> getNumber() { return number; } public void setNumber(List<?> number) { this.number = number; } public static class NeighborhoodBean { private List<?> name; private List<?> type; public List<?> getName() { return name; } public void setName(List<?> name) { this.name = name; } public List<?> getType() { return type; } public void setType(List<?> type) { this.type = type; } } public static class BuildingBean { private List<?> name; private List<?> type; public List<?> getName() { return name; } public void setName(List<?> name) { this.name = name; } public List<?> getType() { return type; } public void setType(List<?> type) { this.type = type; } } } } }