public class LocationUtils {
private static final String TAG = "Utils.Location";
private volatile static LocationUtils uniqueInstance;
private LocationManager locationManager;
private Context mContext;
private AddressCallback addressCallback;
public AddressCallback getAddressCallback() {
return addressCallback;
}
public void setAddressCallback(AddressCallback addressCallback) {
this.addressCallback = addressCallback;
if (isInit) {
showLocation();
} else {
isInit = true;
}
}
private static Location location;
private boolean isInit = false;//是否加载过
private LocationUtils(Context context) {
mContext = context;
//getLocation();
locationManager = (LocationManager) mContext.getSystemService(Context.LOCATION_SERVICE);
}
public static LocationUtils getInstance(Context context) {
if (uniqueInstance == null) {
synchronized (LocationUtils.class) {
if (uniqueInstance == null) {
uniqueInstance = new LocationUtils(context);
}
}
}
return uniqueInstance;
}
/**
* 添加回调事件
*
* @param addressCallback
*/
private void addAddressCallback(AddressCallback addressCallback) {
if (isInit) {
showLocation();
}
}
public void start(){
getLocation();
}
private void getLocation() {
//1.获取位置管理器
//locationManager = (LocationManager) mContext.getSystemService(Context.LOCATION_SERVICE);
//添加用户权限申请判断
if (ActivityCompat.checkSelfPermission(mContext, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED
&& ActivityCompat.checkSelfPermission(mContext, Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
Log.w(TAG, "请开启权限");
return;
}
//2.获取位置提供器,GPS或是NetWork
// 获取所有可用的位置提供器
List<String> providerList = locationManager.getProviders(true);
String locationProvider;
if (providerList.contains(LocationManager.GPS_PROVIDER)) {
//GPS 定位的精准度比较高,但是非常耗电。
Log.v(TAG, "GPS_PROVIDER");
locationProvider = LocationManager.GPS_PROVIDER;
} else if (providerList.contains(LocationManager.NETWORK_PROVIDER)) {//Google服务被墙不可用
//网络定位的精准度稍差,但耗电量比较少。
Log.v(TAG, "NETWORK_PROVIDER");
locationProvider = LocationManager.NETWORK_PROVIDER;
} else {
Log.v(TAG, "NO_PROVIDER");
// 当没有可用的位置提供器时,弹出Toast提示用户
Intent intent = new Intent();
intent.setAction(Settings.ACTION_LOCATION_SOURCE_SETTINGS);
mContext.startActivity(intent);
return;
}
//3.获取上次的位置,一般第一次运行,此值为null
location = locationManager.getLastKnownLocation(locationProvider);
if (location != null) {
// 显示当前设备的位置信息
Log.v(TAG, "显示当前设备的位置信息");
showLocation();
} else {//当GPS信号弱没获取到位置的时候可从网络获取
Log.v(TAG, "Google服务被墙的解决办法");
getLngAndLatWithNetwork();//Google服务被墙的解决办法
}
// 监视地理位置变化,第二个和第三个参数分别为更新的最短时间minTime和最短距离minDistace
//LocationManager 每隔 5 秒钟会检测一下位置的变化情况,当移动距离超过 10 米的时候,
// 就会调用 LocationListener 的 onLocationChanged() 方法,并把新的位置信息作为参数传入。
//locationManager.requestLocationUpdates(locationProvider, 5000, 10, locationListener);
}
//获取经纬度
private void showLocation() {
if (location == null) {
getLocation();
} else {
double latitude = location.getLatitude();//纬度
double longitude = location.getLongitude();//经度
if (addressCallback != null) {
addressCallback.onGetLocation(latitude, longitude);
}
getAddress(latitude, longitude);
}
}
private void getAddress(double latitude, double longitude) {
//Geocoder通过经纬度获取具体信息
Geocoder gc = new Geocoder(mContext, Locale.getDefault());
try {
List<Address> locationList = gc.getFromLocation(latitude, longitude, 1);
if (locationList != null && locationList.size() > 0) {
if (addressCallback != null) {
addressCallback.onGetAddress(locationList.get(0));
}
}
} catch (IOException e) {
e.printStackTrace();
}
}
private void removeLocationUpdatesListener() {
if (locationManager != null) {
uniqueInstance = null;
locationManager.removeUpdates(locationListener);
}
}
private final LocationListener locationListener = new LocationListener() {
// Provider的状态在可用、暂时不可用和无服务三个状态直接切换时触发此函数
@Override
public void onStatusChanged(String provider, int status, Bundle arg2) {
}
// Provider被enable时触发此函数,比如GPS被打开
@Override
public void onProviderEnabled(String provider) {
}
// Provider被disable时触发此函数,比如GPS被关闭
@Override
public void onProviderDisabled(String provider) {
}
//当坐标改变时触发此函数,如果Provider传进相同的坐标,它就不会被触发
@Override
public void onLocationChanged(Location location) {
Log.v(TAG, "onLocationChanged>>>" + location.toString());
}
};
//从网络获取经纬度
private void getLngAndLatWithNetwork() {
//添加用户权限申请判断
if (ActivityCompat.checkSelfPermission(mContext, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED
&& ActivityCompat.checkSelfPermission(mContext, Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
return;
}
LocationManager locationManager = (LocationManager) mContext.getSystemService(Context.LOCATION_SERVICE);
locationManager.requestLocationUpdates(LocationManager.NETWORK_PROVIDER, 5000, 10, locationListener);
location = locationManager.getLastKnownLocation(LocationManager.NETWORK_PROVIDER);
showLocation();
}
public interface AddressCallback {
void onGetAddress(Address address);
void onGetLocation(double lat, double lng);
}
}
网友评论