Android 高德地图的定位功能,以及动态开启权限

来源:互联网 发布:柬埔寨翻译中文软件 编辑:程序博客网 时间:2024/05/29 17:10

配置工程

  1. Eclipse 配置工程:http://lbs.amap.com/api/android-location-sdk/guide/create-project/eclipse-create-project
  2. Android Studio 配置工程:http://lbs.amap.com/api/android-location-sdk/guide/create-project/android-studio-create-project

配置AndroidManifest.xml

1、权限

    <!--用于进行网络定位-->    <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>

2.设置高德的key

  <!--设置高德地图的key-->        <meta-data            android:name="com.amap.api.v2.apikey"            android:value="您的key" />        <service android:name="com.amap.api.location.APSService" />

获取key的帮助文档:http://lbs.amap.com/api/android-location-sdk/guide/create-project/get-key

3.初始化定位

请在主线程中声明AMapLocationClient类对象,需要传Context类型的参数。推荐用getApplicationConext()方法获取全进程有效的context。

//声明AMapLocationClient类对象public AMapLocationClient mLocationClient = null;//声明定位回调监听器public AMapLocationListener mLocationListener = new AMapLocationListener();//初始化定位mLocationClient = new AMapLocationClient(getApplicationContext());//设置定位回调监听mLocationClient.setLocationListener(mLocationListener);

4.配置参数并启动定位

创建AMapLocationClientOption对象
AMapLocationClientOption对象用来设置发起定位的模式和相关参数等。

案例效果图

这里写图片描述

下面是具体代码:

MainActivity

public class MainActivity extends AppCompatActivity {    Button btn;    TextView tv;    /**     * 需要进行检测的权限数组     */    protected String[] needPermissions = {            Manifest.permission.ACCESS_COARSE_LOCATION,            Manifest.permission.ACCESS_FINE_LOCATION,            Manifest.permission.WRITE_EXTERNAL_STORAGE,            Manifest.permission.READ_EXTERNAL_STORAGE,            Manifest.permission.READ_PHONE_STATE    };    private static final int PERMISSON_REQUESTCODE = 0;    /**     * 判断是否需要检测,防止不停的弹框     */    private boolean isNeedCheck = true;    //声明AMapLocationClient类对象    public AMapLocationClient mLocationClient = null;    //声明定位回调监听器    //public AMapLocationListener mLocationListener = new AMapLocationListener();    // public AMapLocationListener mLocationListener;    //声明AMapLocationClientOption对象    public AMapLocationClientOption mLocationOption = new AMapLocationClientOption();    @Override    protected void onCreate(Bundle savedInstanceState) {        requestWindowFeature(Window.FEATURE_NO_TITLE);        getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN);        super.onCreate(savedInstanceState);        setContentView(R.layout.activity_main);        btn = (Button) findViewById(R.id.btn_get);        tv = (TextView) findViewById(R.id.tv_text);        //初始化定位        initLocation();        //设置定位模式为AMapLocationMode.Hight_Accuracy,高精度模式。        mLocationOption.setLocationMode(AMapLocationClientOption.AMapLocationMode.Hight_Accuracy);        btn.setOnClickListener(new View.OnClickListener() {            @Override            public void onClick(View view) {                //定位                //启动定位                //            mLocationClient.startLocation();                //设置参数                //    mLocationClient.setLocationOption(getDefaultOption());                Log.e("进入", "点击事件" + "=========================================================================");                //定位监听器//                mLocationListener = new AMapLocationListener() {//                    @Override//                    public void onLocationChanged(AMapLocation aMapLocation) {//                        ////                        Log.e("进入", "回调" + "=========================================================================");//                        if (aMapLocation != null) {//                            if (aMapLocation.getErrorCode() == 0) {//                                //可在其中解析amapLocation获取相应内容。//                                Log.e("进入", "回调返回" + "aMapLocation != null=========================================================================");//                                aMapLocation.getLocationType();//获取当前定位结果来源,如网络定位结果,详见定位类型表//                                aMapLocation.getLatitude();//获取纬度//                                aMapLocation.getLongitude();//获取经度//                                aMapLocation.getAccuracy();//获取精度信息//                                aMapLocation.getAddress();//地址,如果option中设置isNeedAddress为false,则没有此结果,网络定位结果中会有地址信息,GPS定位不返回地址信息。//                                aMapLocation.getCountry();//国家信息//                                aMapLocation.getProvince();//省信息//                                aMapLocation.getCity();//城市信息//                                aMapLocation.getDistrict();//城区信息//                                aMapLocation.getStreet();//街道信息//                                aMapLocation.getStreetNum();//街道门牌号信息//                                aMapLocation.getCityCode();//城市编码//                                aMapLocation.getAdCode();//地区编码//                                aMapLocation.getAoiName();//获取当前定位点的AOI信息//                                aMapLocation.getBuildingId();//获取当前室内定位的建筑物Id//                                aMapLocation.getFloor();//获取当前室内定位的楼层//                                //   aMapLocation.getGpsStatus();//获取GPS的当前状态//                                //获取定位时间//                                SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");//                                Date date = new Date(aMapLocation.getTime());//                                df.format(date);//                                tv.setText(aMapLocation.getAddress());////                                String s = aMapLocation.getAddress();//                                Log.e("定位成功,", "地址" + aMapLocation.getAddress());////                                if (!TextUtils.isEmpty(s)) {////                                    stopLocation();////                                }//////                            } else {//                                //定位失败时,可通过ErrCode(错误码)信息来确定失败的原因,errInfo是错误信息,详见错误码表。//                                Log.e("AmapError", "location Error, ErrCode:"//                                        + aMapLocation.getErrorCode() + ", errInfo:"//                                        + aMapLocation.getErrorInfo());//                            }//                        }//                    }//                };                //开始定位                startLocation();            }        });    }    private void startLocation() {        //根据控件的选择,重新设置定位参数        //resetOption();        // 设置定位参数        mLocationClient.setLocationOption(mLocationOption);        // 启动定位        mLocationClient.startLocation();    }    private void initLocation() {        //初始化client        mLocationClient = new AMapLocationClient(this.getApplicationContext());        //设置定位参数        mLocationClient.setLocationOption(getDefaultOption());        // 设置定位监听        mLocationClient.setLocationListener(mLocationListener);    }    /**     * 停止定位     *     * @author     * @since 2.8.0     */    private void stopLocation() {        // 停止定位        mLocationClient.stopLocation();    }    @Override    protected void onDestroy() {        super.onDestroy();        destroyLocation();    }    private void destroyLocation() {        if (null != mLocationClient) {            mLocationClient.onDestroy();            mLocationClient = null;            mLocationOption = null;        }    }    /**     * 默认的定位参数     *     * @author     * @since 2.8.0     */    private AMapLocationClientOption getDefaultOption() {        AMapLocationClientOption mOption = new AMapLocationClientOption();        mOption.setLocationMode(AMapLocationClientOption.AMapLocationMode.Hight_Accuracy);//可选,设置定位模式,可选的模式有高精度、仅设备、仅网络。默认为高精度模式        mOption.setGpsFirst(false);//可选,设置是否gps优先,只在高精度模式下有效。默认关闭        //mOption.setHttpTimeOut(30000);//可选,设置网络请求超时时间。默认为30秒。在仅设备模式下无效        //   mOption.setInterval(2000);//可选,设置定位间隔。默认为2秒        mOption.setNeedAddress(true);//可选,设置是否返回逆地理地址信息。默认是true        //   mOption.setOnceLocation(false);//可选,设置是否单次定位。默认是false        mLocationOption.setOnceLocation(true);  //获取一次定位结果:        mOption.setOnceLocationLatest(false);//可选,设置是否等待wifi刷新,默认为false.如果设置为true,会自动变为单次定位,持续定位时不要使用        AMapLocationClientOption.setLocationProtocol(AMapLocationClientOption.AMapLocationProtocol.HTTP);//可选, 设置网络请求的协议。可选HTTP或者HTTPS。默认为HTTP        mOption.setSensorEnable(false);//可选,设置是否使用传感器。默认是false        mOption.setWifiScan(true); //可选,设置是否开启wifi扫描。默认为true,如果设置为false会同时停止主动刷新,停止以后完全依赖于系统刷新,定位位置可能存在误差        mOption.setLocationCacheEnable(true); //可选,设置是否使用缓存定位,默认为true        return mOption;    }    /**     * 定位监听     */    AMapLocationListener mLocationListener = new AMapLocationListener() {        @Override        public void onLocationChanged(AMapLocation aMapLocation) {            if (null != aMapLocation) {                //解析定位结果                String result = Utils.getLocationStr(aMapLocation);                tv.setText(result);                Log.e("定位", "aMapLocation is null" + result);            } else {                tv.setText("定位失败,aMapLocation is null");                Log.e("定位失败", "aMapLocation is null");            }        }    };    //----------以下动态获取权限---------    @Override    protected void onResume() {        super.onResume();        if (isNeedCheck) {            checkPermissions(needPermissions);        }    }    /**     * 检查权限     *     * @param     * @since 2.5.0     */    private void checkPermissions(String... permissions) {        //获取权限列表        List<String> needRequestPermissonList = findDeniedPermissions(permissions);        if (null != needRequestPermissonList                && needRequestPermissonList.size() > 0) {            //list.toarray将集合转化为数组            ActivityCompat.requestPermissions(this,                    needRequestPermissonList.toArray(new String[needRequestPermissonList.size()]),                    PERMISSON_REQUESTCODE);        }    }    /**     * 获取权限集中需要申请权限的列表     *     * @param permissions     * @return     * @since 2.5.0     */    private List<String> findDeniedPermissions(String[] permissions) {        List<String> needRequestPermissonList = new ArrayList<String>();        //for (循环变量类型 循环变量名称 : 要被遍历的对象)        for (String perm : permissions) {            if (ContextCompat.checkSelfPermission(this,                    perm) != PackageManager.PERMISSION_GRANTED                    || ActivityCompat.shouldShowRequestPermissionRationale(                    this, perm)) {                needRequestPermissonList.add(perm);            }        }        return needRequestPermissonList;    }    /**     * 检测是否说有的权限都已经授权     *     * @param grantResults     * @return     * @since 2.5.0     */    private boolean verifyPermissions(int[] grantResults) {        for (int result : grantResults) {            if (result != PackageManager.PERMISSION_GRANTED) {                return false;            }        }        return true;    }    @Override    public void onRequestPermissionsResult(int requestCode,                                           String[] permissions, int[] paramArrayOfInt) {        if (requestCode == PERMISSON_REQUESTCODE) {            if (!verifyPermissions(paramArrayOfInt)) {      //没有授权                showMissingPermissionDialog();              //显示提示信息                isNeedCheck = false;            }        }    }    /**     * 显示提示信息     *     * @since 2.5.0     */    private void showMissingPermissionDialog() {        AlertDialog.Builder builder = new AlertDialog.Builder(this);        builder.setTitle(R.string.notifyTitle);        builder.setMessage(R.string.notifyMsg);        // 拒绝, 退出应用        builder.setNegativeButton(R.string.cancel,                new DialogInterface.OnClickListener() {                    @Override                    public void onClick(DialogInterface dialog, int which) {                        finish();                    }                });        builder.setPositiveButton(R.string.setting,                new DialogInterface.OnClickListener() {                    @Override                    public void onClick(DialogInterface dialog, int which) {                        startAppSettings();                    }                });        builder.setCancelable(false);        builder.show();    }    /**     * 启动应用的设置     *     * @since 2.5.0     */    private void startAppSettings() {        Intent intent = new Intent(                Settings.ACTION_APPLICATION_DETAILS_SETTINGS);        intent.setData(Uri.parse("package:" + getPackageName()));        startActivity(intent);    }    @Override    public boolean onKeyDown(int keyCode, KeyEvent event) {        if (keyCode == KeyEvent.KEYCODE_BACK) {            this.finish();            return true;        }        return super.onKeyDown(keyCode, event);    }}

Utils

public class Utils {    /**     *  开始定位     */    public final static int MSG_LOCATION_START = 0;    /**     * 定位完成     */    public final static int MSG_LOCATION_FINISH = 1;    /**     * 停止定位     */    public final static int MSG_LOCATION_STOP= 2;    public final static String KEY_URL = "URL";    public final static String URL_H5LOCATION = "file:///android_asset/location.html";    /**     * 根据定位结果返回定位信息的字符串     * @param loc     * @return     */    public synchronized static String getLocationStr(AMapLocation location){        if(null == location){            return null;        }        StringBuffer sb = new StringBuffer();        //errCode等于0代表定位成功,其他的为定位失败,具体的可以参照官网定位错误码说明        if(location.getErrorCode() == 0){            sb.append("定位成功" + "\n");            sb.append("定位类型: " + location.getLocationType() + "\n");            sb.append("经    度    : " + location.getLongitude() + "\n");            sb.append("纬    度    : " + location.getLatitude() + "\n");            sb.append("精    度    : " + location.getAccuracy() + "米" + "\n");            sb.append("提供者    : " + location.getProvider() + "\n");            sb.append("速    度    : " + location.getSpeed() + "米/秒" + "\n");            sb.append("角    度    : " + location.getBearing() + "\n");            // 获取当前提供定位服务的卫星个数            sb.append("星    数    : " + location.getSatellites() + "\n");            sb.append("国    家    : " + location.getCountry() + "\n");            sb.append("省            : " + location.getProvince() + "\n");            sb.append("市            : " + location.getCity() + "\n");            sb.append("城市编码 : " + location.getCityCode() + "\n");            sb.append("区            : " + location.getDistrict() + "\n");            sb.append("区域 码   : " + location.getAdCode() + "\n");            sb.append("地    址    : " + location.getAddress() + "\n");            sb.append("兴趣点    : " + location.getPoiName() + "\n");            //定位完成的时间            sb.append("定位时间: " + formatUTC(location.getTime(), "yyyy-MM-dd HH:mm:ss") + "\n");        } else {            //定位失败            sb.append("定位失败" + "\n");            sb.append("错误码:" + location.getErrorCode() + "\n");            sb.append("错误信息:" + location.getErrorInfo() + "\n");            sb.append("错误描述:" + location.getLocationDetail() + "\n");        }        //定位之后的回调时间        sb.append("回调时间: " + formatUTC(System.currentTimeMillis(), "yyyy-MM-dd HH:mm:ss") + "\n");        return sb.toString();    }    private static SimpleDateFormat sdf = null;    public synchronized static String formatUTC(long l, String strPattern) {        if (TextUtils.isEmpty(strPattern)) {            strPattern = "yyyy-MM-dd HH:mm:ss";        }        if (sdf == null) {            try {                sdf = new SimpleDateFormat(strPattern, Locale.CHINA);            } catch (Throwable e) {            }        } else {            sdf.applyPattern(strPattern);        }        return sdf == null ? "NULL" : sdf.format(l);    }}

几个String

 <string name="notifyTitle">提示</string>    <string name="notifyMsg">当前应用缺少必要权限。\n\n请点击\"设置\"-\"权限\"-打开所需权限。</string>    <string name="gpsNotifyMsg">当前应用需要打开定位功能。\n\n请点击\"设置\"-\"定位服务\"-打开定位功能。</string>    <string name="setting">设置</string>    <string name="cancel">取消</string>

关于动态权限

1.检查限限,如果没有就申请,申请权限的方法如下:
ActivityCompat.requestPermissions(this,needRequestPermissonList.toArray(newString[needRequestPermissonList.size()]),PERMISSON_REQUESTCODE);
第一个参数是activity,第二个参数是权限的数组,是数组的格式,,第三个参数是requestCode,requestPermissions()方法内部已经做了判断
2.回调方法
onRequestPermissionsResult(int requestCode,String[] permissions, int[] paramArrayOfInt)
通过判断int[] paramArrayOfInt返回的结果是否 == PackageManager.PERMISSION_GRANTED
如果不等于,则是没有授权,弹出对话框,进行用户选择 如果==于,则说明已经授权完成

原创粉丝点击