超详细解析定位
坐标—LatLng
定位中用得最多的是坐标(也就是经纬度),那么我们首先搞清楚什么是坐标:
LatLng 类:地理坐标基本数据结构。
[thead]
描述 | 方法名 |
[/thead]
构造函数 | LatLng(double latitude, double longitude) |
字段详细资料[thead]
描述 | 字段名 | 定义 |
[/thead]
纬度 | latitude | public final double latitude |
经度 | longitude | public final double longitude |
提醒:经纬度我经常搞错,不知道为什么,大家特别在操作坐标的时候要格外注意。经纬度的数据类型是double
类型的。坐标拾取系统
百度的坐标拾取系统每次大家想知道一个地方的坐标或者想拿几个示例坐标,那么就可以用这个。鼠标点击地图上任意一处地方就会得到该地点的坐标(显示在右上角方框里);效果图(重点看一下红框里的内容):地理范围数据结构—LatLngBounds
地理范围数据结构,由西南以及东北坐标点确认。虽然说用的不多,但它和坐标有点亲属关系,所以使不使用我们都介绍。
一般有XXX.Builder
的希望大家多多使用,尽量不要new
,当然了,有的类是有构造方法的有的没有;嵌套类概要:[thead]
限定符和类型 | 类 | 说明 |
[/thead]
static class | LatLngBounds.Builder | 地理范围构造器 |
字段概要:
[thead]
限定符和类型 | 字段 | 说明 |
[/thead]
LatLng | northeast | 该地理范围东北坐标 |
LatLng | southwest | 该地理范围西南坐标 |
方法概要:
[thead]
限定符和类型 | 方法 | 说明 |
[/thead]
boolean | contains(LatLng point) | 判断该地理范围是否包含一个地理位置 |
LatLng | getCenter() | 获取该地理范围的中心地理坐标 |
方法详细资料:
public boolean contains(LatLng point)
判断该地理范围是否包含一个地理位置
参数:
point - 被判断的地理位置
返回:
该地理范围是否包含一个地理位置
public LatLng getCenter()
获取该地理范围的中心地理坐标
返回:
该地理范围的中心地理坐标
地理范围构造器—LatLngBounds.Builder
构造器概要 :
[thead]
构造器 | 说明 |
[/thead]
LatLngBounds.Builder() | 构造函数 |
方法概要:
[thead]
限定符和类型 | 方法 | 说明 |
[/thead]
LatLngBounds | build() | 创建地理范围对象 |
LatLngBounds.Builder | include(LatLng point) | 让该地理范围包含一个地理位置坐标 |
方法详细资料:
public LatLngBounds build()
创建地理范围对象
返回:
创建出的地理范围对象
public LatLngBounds.Builder include(LatLng point)
让该地理范围包含一个地理位置坐标
参数:
point - 地理位置坐标
返回:
该构造器对象
使用范例:
mBDMap.setOnMapLoadedCallback(new BaiduMap.OnMapLoadedCallback() {
@Override
public void onMapLoaded() {
//坐标范围
LatLng northeast = new LatLng(121.445541, 31.192286);
LatLng southwest = new LatLng(121.441624, 31.189922);
LatLngBounds llb = new LatLngBounds.Builder().include(northeast).include(southwest).build();
boolean isHas = llb.contains(new LatLng(121.443564, 31.190795));
Log.v("此功能地图加载完毕的时候调用", "有还是没有" + isHas + ",东北:" + llb.northeast + "西南:" + llb.southwest);
}
});
简单定位
创建
activity_location.xml
:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent">
<com.baidu.mapapi.map.MapView
android:id="@+id/location_bdmap"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:clickable="true"></com.baidu.mapapi.map.MapView>
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_marginTop="80dp"
android:background="#9e9e9e"
android:minWidth="100dp"
android:orientation="vertical"
android:padding="2dp">
<RadioGroup
android:id="@+id/location_rg"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:contentDescription="定位ICON">
<RadioButton
android:id="@+id/location_rb_defaulticon"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:clickable="true"
android:text="默认图标" />
<RadioButton
android:id="@+id/location_rb_customicon"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="自定义图标" />
</RadioGroup>
</LinearLayout>
<Button
android:id="@+id/location_btn"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_alignParentTop="true"
android:layout_marginRight="25dp"
android:layout_marginTop="10dp" />
</RelativeLayout>
编写
LocationDemo
类继承自
BaseActivity:
/**
* Activity基类
*/
public class BaseActivity extends FragmentActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
//在使用SDK各组件之前初始化context信息,传入ApplicationContext
//注意该方法要再setContentView方法之前实现
SDKInitializer.initialize(getApplicationContext());
}
}
public class LocationDemo extends BaseActivity implements View.OnClickListener, RadioGroup.OnCheckedChangeListener, BDLocationListener {
private MapView mMapView;
private BaiduMap mBDMap;
//定位
private Button requestLocBtn;
//定位图层显示方式
private MyLocationConfiguration.LocationMode mCurrentMode;
//用户自定义定位图标
private BitmapDescriptor mCurrentMarker;
//单选按钮组
private RadioGroup rg;
//定位相关
private LocationClient mLocClient;
//是否第一次定位
private boolean isFirstLoc = true;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_location);
initView();
}
private void initView() {
//请求定位
requestLocBtn = (Button) findViewById(R.id.location_btn);
//定位图层显示方式
mCurrentMode = MyLocationConfiguration.LocationMode.NORMAL;
requestLocBtn.setText("普通");
requestLocBtn.setOnClickListener(this);
//单选按钮组
rg = (RadioGroup) findViewById(R.id.location_rg);
rg.setOnCheckedChangeListener(this);
//地图初始化
mMapView = (MapView) findViewById(R.id.location_bdmap);
mBDMap = mMapView.getMap();
//开启定位图层
mBDMap.setMyLocationEnabled(true);
//定位初始化
mLocClient = new LocationClient(this);
mLocClient.registerLocationListener(this);
LocationClientOption option = new LocationClientOption();
option.setOpenGps(true);//打开GPS
option.setCoorType("bd09ll");//设置坐标类型
option.setScanSpan(1000);//设置请求间隔时间
mLocClient.setLocOption(option);//加载配置
mLocClient.start();//开始定位
}
//定位按钮点击事件
@Override
public void onClick(View v) {
switch (mCurrentMode) {
//普通态:更新定位数据时不对地图做任何操作
case NORMAL:
requestLocBtn.setText("跟随");
mCurrentMode = MyLocationConfiguration.LocationMode.FOLLOWING;
break;
//罗盘态,显示定位方向圈,保持定位图标在地图中心
case COMPASS:
requestLocBtn.setText("普通");
mCurrentMode = MyLocationConfiguration.LocationMode.NORMAL;
break;
//跟随态,保持定位图标在地图中心
case FOLLOWING:
requestLocBtn.setText("罗盘");
mCurrentMode = MyLocationConfiguration.LocationMode.COMPASS;
break;
}
//配置定位图层显示方式
mBDMap.setMyLocationConfigeration(new MyLocationConfiguration(mCurrentMode, true, mCurrentMarker));
//开始定位
mLocClient.start();
}
//单选事件
@Override
public void onCheckedChanged(RadioGroup group, int checkedId) {
switch (checkedId) {
case R.id.location_rb_defaulticon:
//传入null则恢复默认图标
mCurrentMarker = null;
break;
case R.id.location_rb_customicon:
//修改为自定义的Marker
mCurrentMarker = BitmapDescriptorFactory.fromResource(R.mipmap.ic_launcher);
break;
}
//配置定位图层显示方式
mBDMap.setMyLocationConfigeration(new MyLocationConfiguration(mCurrentMode, true, mCurrentMarker));
}
//定位监听
@Override
public void onReceiveLocation(BDLocation bdLocation) {
//如果bdLocation为空或mapView销毁后不再处理新数据接收的位置
if (bdLocation == null || mMapView == null) {
return;
}
//定位数据
MyLocationData data = new MyLocationData.Builder()
//精度(半径)
.accuracy(bdLocation.getRadius())
//此处设置开发者获取到的方向信息,顺时针0-360
.direction(100)
.latitude(bdLocation.getLatitude())
.longitude(bdLocation.getLongitude()).build();
//设置定位数据
mBDMap.setMyLocationData(data);
//是否是第一次定位
if (isFirstLoc) {
isFirstLoc = false;
LatLng ll = new LatLng(bdLocation.getLatitude(), bdLocation.getLongitude());
MapStatusUpdate msu = MapStatusUpdateFactory.newLatLng(ll);
mBDMap.animateMapStatus(msu);
}
}
@Override
protected void onResume() {
super.onResume();
mMapView.onResume();
}
@Override
protected void onPause() {
super.onPause();
mMapView.onPause();
}
@Override
protected void onDestroy() {
super.onDestroy();
//退出时销毁定位
mLocClient.stop();
//关闭定位图层
mBDMap.setMyLocationEnabled(false);
mMapView.onDestroy();
mMapView = null;
}
}
运行效果图:
配置定位图层显示方式—MyLocationConfiguration
构造器概要:
[thead]
构造器 | 说明 |
[/thead]
MyLocationConfiguration(MyLocationConfiguration.LocationMode mode, boolean enableDirection, BitmapDescriptor customMarker) | 构造函数 |
构造器详细资料:
public MyLocationConfiguration(MyLocationConfiguration.LocationMode mode,
boolean enableDirection,
BitmapDescriptor customMarker)
构造函数
参数:
mode - 定位图层显示方式, 默认为 LocationMode.NORMAL 普通态
enableDirection - 是否允许显示方向信息
customMarker - 设置用户自定义定位图标,可以为 null
updateTimeEscap - 图层刷新频率,单位ms,若使用默认值,输入0即可,默认为100ms
嵌套类概要 :
[thead]
限定符和类型 | 类 | 说明 |
[/thead]
static class | MyLocationConfiguration.LocationMode | 定位图层显示方式 |
字段概要:
[thead]
限定符和类型 | 字段 | 说明 |
[/thead]
BitmapDescriptor | customMarker | 用户自定义定位图标 |
boolean | enableDirection | 是否允许显示方向信息 |
MyLocationConfiguration.LocationMode | locationMode | 定位图层显示方式 |
定位图层显示方式—MyLocationConfiguration.LocationMode
枚举常量概要 :
[thead]
枚举常量 | 说明 |
[/thead]
COMPASS | 罗盘态,显示定位方向圈,保持定位图标在地图中心 |
FOLLOWING | 跟随态,保持定位图标在地图中心 |
NORMAL | 普通态: 更新定位数据时不对地图做任何操作 |
方法概要:
[thead]
限定符和类型 | 类 | 说明 |
[/thead]
static MyLocationConfiguration.LocationMode | valueOf(java.lang.String name) | 返回带有指定名称的该类型的枚举常量 |
static MyLocationConfiguration.LocationMode[] | values() | 按照声明该枚举类型的常量的顺序, 返回包含这些常量的数组 |
方法详细资料:
public static MyLocationConfiguration.LocationMode[] values()
按照声明该枚举类型的常量的顺序, 返回 包含这些常量的数组。该方法可用于迭代 常量, 如下所示:
for (MyLocationConfiguration.LocationMode c : MyLocationConfiguration.LocationMode.values())
System.out.println(c);
返回:
按照声明该枚举类型的常量的顺序, 返回 包含这些常量的数组
public static MyLocationConfiguration.LocationMode valueOf(java.lang.String name)
返回带有指定名称的该类型的枚举常量。 字符串必须与用于声明该类型的枚举常量的 标识符完全匹配。(不允许有多余 的空格字符。)
参数:
name - 要返回的枚举常量的名称。
返回:
返回带有指定名称的枚举常量
抛出:
如果该枚举类型没有带有指定名称的常量, - 则抛出 IllegalArgumentException
如果参数为空值, - 则抛出 NullPointerException
定位数据—MyLocationData
嵌套类概要 :
[thead]
限定符和类型 | 类 | 说明 |
[/thead]
static class | MyLocationData.Builder | 定位数据建造器 |
字段概要:
[thead]
限定符和类型 | 字段 | 说明 |
[/thead]
float | accuracy | 定位精度 |
float | direction | GPS定位时方向角度 |
double | latitude | 百度纬度坐标 |
double | longitude | 百度经度坐标 |
int | satellitesNum | GPS定位时卫星数目 |
float | speed | GPS定位时速度 |
定位数据建造器—MyLocationData.Builder
构造器概要:
[thead]
构造器 | 说明 |
[/thead]
MyLocationData.Builder() | 构造函数 |
方法概要 :
[thead]
限定符和类型 | 方法 | 说明 |
[/thead]
MyLocationData.Builder | accuracy(float accuracy) | 设置定位数据的精度信息,单位:米 |
MyLocationData | build() | 构建生成定位数据对象 |
MyLocationData.Builder | direction(float direction) | 设置定位数据的方向信息 |
MyLocationData.Builder | latitude(double lat) | 设置定位数据的纬度 |
MyLocationData.Builder | longitude(double lng) | 设置定位数据的经度 |
MyLocationData.Builder | satellitesNum(int num) | 设置定位数据的卫星数目 |
MyLocationData.Builder | speed(float speed) | 设置定位数据的速度 |
方法详细资料:
public MyLocationData.Builder latitude(double lat)
设置定位数据的纬度
参数:
lat - 纬度
返回:
该构造器对象
public MyLocationData.Builder longitude(double lng)
设置定位数据的经度
参数:
lng - 经度
返回:
该构造器对象
public MyLocationData.Builder speed(float speed)
设置定位数据的速度
参数:
speed - 速度
返回:
该构造器对象
public MyLocationData.Builder direction(float direction)
设置定位数据的方向信息
参数:
direction - 方向
返回:
该构造器对象
public MyLocationData.Builder accuracy(float accuracy)
设置定位数据的精度信息,单位:米
参数:
accuracy - 精度信息,单位:米
返回:
该构造器对象
public MyLocationData.Builder satellitesNum(int num)
设置定位数据的卫星数目
参数:
num - 卫星数目
返回:
该构造器对象
public MyLocationData build()
构建生成定位数据对象
返回:
生成定位数据对象
销毁说明
看我们的最后一个方法[
onDestroy()
] :
@Override
protected void onDestroy() {
super.onDestroy();
//退出时销毁定位
mLocClient.stop();
//关闭定位图层
mBDMap.setMyLocationEnabled(false);
mMapView.onDestroy();
mMapView = null;
}
这里我们在编写的时候一定要注意代码顺序,其次一定要
mMapView = null;
释放内存;这里涉及到一个内存回收的知识点:
如果
stu=null
,也就是
new Student();
这个实例没有被引用,那么它在堆内存中被视为垃圾,虚拟机不会马上回收它,但肯定会回收它。