private GoogleMap map;
LocationManager lm;
LocationListener ll;
Location l;
LatLng pos;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.start_layout);
lm = (LocationManager) this.getSystemService(Context.LOCATION_SERVICE);
ll = new LocationListener() {
@Override
public void onLocationChanged(Location location) {
l = (Location) location;
}
@Override
public void onStatusChanged(String provider, int status, Bundle extras) {}
@Override
public void onProviderEnabled(String provider) {}
@Override
public void onProviderDisabled(String provider) {}
};
SupportMapFragment mapFragment = (SupportMapFragment) getSupportFragmentManager()
.findFragmentById(R.id.nMap);
mapFragment.getMapAsync(this);
}
@Override
public void onMapReady(GoogleMap googleMap) {
map = googleMap;
if(ContextCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED) {
lm.requestLocationUpdates(lm.NETWORK_PROVIDER, 0, 0, ll);
}
pos = new LatLng(l.getLatitude(), l.getLongitude());
// Add a marker in Sydney and move the camera
map.setMyLocationEnabled(true);
map.addMarker(new MarkerOptions().position(pos).title("Marker in Sydney"));
map.moveCamera(CameraUpdateFactory.newLatLng(pos));
}
这里是我设置的权限:
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.INTERNET" />
#1 楼
有关将FusedLocationProviderClient与Google Play Services 11及更高版本配合使用的信息:请参见此处:
如何使用FusedLocationProviderClientClient在GoogleMap中获取当前位置
对于使用(现已弃用)FusedLocationProviderApi :
如果您的项目使用的是Google Play Services 10或更低版本,则使用FusedLocationProviderApi是最佳选择。
FusedLocationProviderApi比旧的开源LocationManager API耗电少。
此外,如果您已经在使用Google Play的Google Maps服务,则没有理由不使用它。
这里有一个完整的Activity类,可将Marker放置在当前位置,并将其移动到当前位置。
它还会在运行时检查Android 6及更高版本(棉花糖,牛轧糖,奥利奥)的位置许可。
为了正确处理在Android M / Android 6及更高版本上需要进行位置权限运行时检查,您需要确保用户已在调用
mGoogleMap.setMyLocationEnabled(true)
之前以及在请求位置更新之前为您的应用授予了“位置”权限。public class MapLocationActivity extends AppCompatActivity
implements OnMapReadyCallback,
GoogleApiClient.ConnectionCallbacks,
GoogleApiClient.OnConnectionFailedListener,
LocationListener {
GoogleMap mGoogleMap;
SupportMapFragment mapFrag;
LocationRequest mLocationRequest;
GoogleApiClient mGoogleApiClient;
Location mLastLocation;
Marker mCurrLocationMarker;
@Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
getSupportActionBar().setTitle("Map Location Activity");
mapFrag = (SupportMapFragment) getSupportFragmentManager().findFragmentById(R.id.map);
mapFrag.getMapAsync(this);
}
@Override
public void onPause() {
super.onPause();
//stop location updates when Activity is no longer active
if (mGoogleApiClient != null) {
LocationServices.FusedLocationApi.removeLocationUpdates(mGoogleApiClient, this);
}
}
@Override
public void onMapReady(GoogleMap googleMap)
{
mGoogleMap=googleMap;
mGoogleMap.setMapType(GoogleMap.MAP_TYPE_HYBRID);
//Initialize Google Play Services
if (android.os.Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
if (ContextCompat.checkSelfPermission(this,
Manifest.permission.ACCESS_FINE_LOCATION)
== PackageManager.PERMISSION_GRANTED) {
//Location Permission already granted
buildGoogleApiClient();
mGoogleMap.setMyLocationEnabled(true);
} else {
//Request Location Permission
checkLocationPermission();
}
}
else {
buildGoogleApiClient();
mGoogleMap.setMyLocationEnabled(true);
}
}
protected synchronized void buildGoogleApiClient() {
mGoogleApiClient = new GoogleApiClient.Builder(this)
.addConnectionCallbacks(this)
.addOnConnectionFailedListener(this)
.addApi(LocationServices.API)
.build();
mGoogleApiClient.connect();
}
@Override
public void onConnected(Bundle bundle) {
mLocationRequest = new LocationRequest();
mLocationRequest.setInterval(1000);
mLocationRequest.setFastestInterval(1000);
mLocationRequest.setPriority(LocationRequest.PRIORITY_BALANCED_POWER_ACCURACY);
if (ContextCompat.checkSelfPermission(this,
Manifest.permission.ACCESS_FINE_LOCATION)
== PackageManager.PERMISSION_GRANTED) {
LocationServices.FusedLocationApi.requestLocationUpdates(mGoogleApiClient, mLocationRequest, this);
}
}
@Override
public void onConnectionSuspended(int i) {}
@Override
public void onConnectionFailed(ConnectionResult connectionResult) {}
@Override
public void onLocationChanged(Location location)
{
mLastLocation = location;
if (mCurrLocationMarker != null) {
mCurrLocationMarker.remove();
}
//Place current location marker
LatLng latLng = new LatLng(location.getLatitude(), location.getLongitude());
MarkerOptions markerOptions = new MarkerOptions();
markerOptions.position(latLng);
markerOptions.title("Current Position");
markerOptions.icon(BitmapDescriptorFactory.defaultMarker(BitmapDescriptorFactory.HUE_MAGENTA));
mCurrLocationMarker = mGoogleMap.addMarker(markerOptions);
//move map camera
mGoogleMap.moveCamera(CameraUpdateFactory.newLatLngZoom(latLng,11));
}
public static final int MY_PERMISSIONS_REQUEST_LOCATION = 99;
private void checkLocationPermission() {
if (ContextCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION)
!= PackageManager.PERMISSION_GRANTED) {
// Should we show an explanation?
if (ActivityCompat.shouldShowRequestPermissionRationale(this,
Manifest.permission.ACCESS_FINE_LOCATION)) {
// Show an explanation to the user *asynchronously* -- don't block
// this thread waiting for the user's response! After the user
// sees the explanation, try again to request the permission.
new AlertDialog.Builder(this)
.setTitle("Location Permission Needed")
.setMessage("This app needs the Location permission, please accept to use location functionality")
.setPositiveButton("OK", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialogInterface, int i) {
//Prompt the user once explanation has been shown
ActivityCompat.requestPermissions(MapLocationActivity.this,
new String[]{Manifest.permission.ACCESS_FINE_LOCATION},
MY_PERMISSIONS_REQUEST_LOCATION );
}
})
.create()
.show();
} else {
// No explanation needed, we can request the permission.
ActivityCompat.requestPermissions(this,
new String[]{Manifest.permission.ACCESS_FINE_LOCATION},
MY_PERMISSIONS_REQUEST_LOCATION );
}
}
}
@Override
public void onRequestPermissionsResult(int requestCode,
String permissions[], int[] grantResults) {
switch (requestCode) {
case MY_PERMISSIONS_REQUEST_LOCATION: {
// If request is cancelled, the result arrays are empty.
if (grantResults.length > 0
&& grantResults[0] == PackageManager.PERMISSION_GRANTED) {
// permission was granted, yay! Do the
// location-related task you need to do.
if (ContextCompat.checkSelfPermission(this,
Manifest.permission.ACCESS_FINE_LOCATION)
== PackageManager.PERMISSION_GRANTED) {
if (mGoogleApiClient == null) {
buildGoogleApiClient();
}
mGoogleMap.setMyLocationEnabled(true);
}
} else {
// permission denied, boo! Disable the
// functionality that depends on this permission.
Toast.makeText(this, "permission denied", Toast.LENGTH_LONG).show();
}
return;
}
// other 'case' lines to check for other
// permissions this app might request
}
}
}
activity_main.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical" android:layout_width="match_parent"
android:layout_height="match_parent">
<fragment xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
xmlns:map="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="@+id/map"
tools:context=".MapLocationActivity"
android:name="com.google.android.gms.maps.SupportMapFragment"/>
</LinearLayout>
结果:
如果需要,可以使用AlertDialog显示许可权说明(如果用户拒绝许可权请求或授予许可权,然后在设置中将其撤消,则会发生这种情况):
通过致电
ActivityCompat.requestPermissions()
提示用户输入位置权限:将相机移动到当前位置并放置标记授予“位置”权限时:
评论
很棒的答案,也可以完美地处理片段。
–时钟
16年4月22日在18:29
LocationServices.FusedLocationApi.requestLocationUpdates(mGoogleApiClient,mLocationRequest,this); -II尝试了您的解决方案,我陷入了这一行代码,说“无法解析requestLocationUpdates”
– RoCk RoCk
16年6月1日,下午3:58
@RoCk确保您的导入是导入com.google.android.gms.location.LocationListener ;,有关导入,请参见此处:stackoverflow.com/a/31448567/4409409
–丹尼尔·纽金特(Daniel Nugent)
16年1月1日,下午4:35
@LalindaSampath它在启用WiFi和GPS的情况下效果最佳。它可以在WiFi关闭且启用GPS的情况下工作,但是由于GPS实际上需要使用卫星来定位您,因此可能需要更长的时间才能进行首次位置更新。如果仅使用GPS进行测试,请确保走到外面走动进行测试。
–丹尼尔·纽金特(Daniel Nugent)
16-09-24在18:01
@lalinda是的,Geocoder需要Internet连接才能工作。它可以是WiFi或蜂窝网络,但是您需要有效的数据连接。
–丹尼尔·纽金特(Daniel Nugent)
16-09-25在20:59
#2 楼
抱歉,这太短了,太快了(上面),如果您有MapFragment,还必须进行映射,只需执行以下操作即可:if (ContextCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED) {
googleMap.setMyLocationEnabled(true)
} else {
// Show rationale and request permission.
}
代码在Kotlin中,希望您不要介意。
玩得开心
顺便说一句,我认为这是重复的:在Google Map Fragment中显示当前位置
评论
然后,您应该使用googleMap?.isMyLocationEnabled = true。
– CoolMind
18/12/19在15:21
这在Kotlin之前很久了:)但是是的,似乎是个好主意
–cV2
18/12/20在7:42
它不会将相机移动到您的位置。它仅启用地图上的图标。
– Hamid
11月29日4:24
#3 楼
首先,请确保您的API密钥有效,并将其添加到清单中。<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
这是我的地图活动。其中可能有一些多余的信息,因为它来自我创建的一个较大的项目。import android.content.Intent;
import android.content.IntentSender;
import android.location.Location;
import android.support.v4.app.FragmentActivity;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.Toast;
import com.google.android.gms.common.ConnectionResult;
import com.google.android.gms.common.api.GoogleApiClient;
import com.google.android.gms.location.LocationListener;
import com.google.android.gms.location.LocationRequest;
import com.google.android.gms.location.LocationServices;
import com.google.android.gms.maps.CameraUpdateFactory;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.OnMapReadyCallback;
import com.google.android.gms.maps.SupportMapFragment;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.Marker;
import com.google.android.gms.maps.model.MarkerOptions;
public class MapsActivity extends FragmentActivity implements
GoogleApiClient.ConnectionCallbacks,
GoogleApiClient.OnConnectionFailedListener,
LocationListener {
//These variable are initalized here as they need to be used in more than one methid
private double currentLatitude; //lat of user
private double currentLongitude; //long of user
private double latitudeVillageApartmets= 53.385952001750184;
private double longitudeVillageApartments= -6.599087119102478;
public static final String TAG = MapsActivity.class.getSimpleName();
private final static int CONNECTION_FAILURE_RESOLUTION_REQUEST = 9000;
private GoogleMap mMap; // Might be null if Google Play services APK is not available.
private GoogleApiClient mGoogleApiClient;
private LocationRequest mLocationRequest;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_maps);
setUpMapIfNeeded();
mGoogleApiClient = new GoogleApiClient.Builder(this)
.addConnectionCallbacks(this)
.addOnConnectionFailedListener(this)
.addApi(LocationServices.API)
.build();
// Create the LocationRequest object
mLocationRequest = LocationRequest.create()
.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY)
.setInterval(10 * 1000) // 10 seconds, in milliseconds
.setFastestInterval(1 * 1000); // 1 second, in milliseconds
}
/*These methods all have to do with the map and wht happens if the activity is paused etc*/
//contains lat and lon of another marker
private void setUpMap() {
MarkerOptions marker = new MarkerOptions().position(new LatLng(latitudeVillageApartmets, longitudeVillageApartments)).title("1"); //create marker
mMap.addMarker(marker); // adding marker
}
//contains your lat and lon
private void handleNewLocation(Location location) {
Log.d(TAG, location.toString());
currentLatitude = location.getLatitude();
currentLongitude = location.getLongitude();
LatLng latLng = new LatLng(currentLatitude, currentLongitude);
MarkerOptions options = new MarkerOptions()
.position(latLng)
.title("You are here");
mMap.addMarker(options);
mMap.moveCamera(CameraUpdateFactory.newLatLngZoom((latLng), 11.0F));
}
@Override
protected void onResume() {
super.onResume();
setUpMapIfNeeded();
mGoogleApiClient.connect();
}
@Override
protected void onPause() {
super.onPause();
if (mGoogleApiClient.isConnected()) {
LocationServices.FusedLocationApi.removeLocationUpdates(mGoogleApiClient, this);
mGoogleApiClient.disconnect();
}
}
private void setUpMapIfNeeded() {
// Do a null check to confirm that we have not already instantiated the map.
if (mMap == null) {
// Try to obtain the map from the SupportMapFragment.
mMap = ((SupportMapFragment) getSupportFragmentManager().findFragmentById(R.id.map))
.getMap();
// Check if we were successful in obtaining the map.
if (mMap != null) {
setUpMap();
}
}
}
@Override
public void onConnected(Bundle bundle) {
Location location = LocationServices.FusedLocationApi.getLastLocation(mGoogleApiClient);
if (location == null) {
LocationServices.FusedLocationApi.requestLocationUpdates(mGoogleApiClient, mLocationRequest, this);
}
else {
handleNewLocation(location);
}
}
@Override
public void onConnectionSuspended(int i) {
}
@Override
public void onConnectionFailed(ConnectionResult connectionResult) {
if (connectionResult.hasResolution()) {
try {
// Start an Activity that tries to resolve the error
connectionResult.startResolutionForResult(this, CONNECTION_FAILURE_RESOLUTION_REQUEST);
/*
* Thrown if Google Play services canceled the original
* PendingIntent
*/
} catch (IntentSender.SendIntentException e) {
// Log the error
e.printStackTrace();
}
} else {
/*
* If no resolution is available, display a dialog to the
* user with the error.
*/
Log.i(TAG, "Location services connection failed with code " + connectionResult.getErrorCode());
}
}
@Override
public void onLocationChanged(Location location) {
handleNewLocation(location);
}
}
这里有很多方法很难理解,但是基本上所有的方法都是在暂停时更新地图等。还有连接超时等。很抱歉刚刚发布了这个,我尝试过修复您的代码,但我不知道出了什么问题。
评论
它以什么方式不起作用?崩溃了吗位置错误?还要检查您的logcat是否有任何错误,并将其发布在这里。