【问题标题】:How to directly move camera to current location in Google Maps Android API v2?如何在 Google Maps Android API v2 中直接将相机移动到当前位置?
【发布时间】:2012-12-07 04:07:28
【问题描述】:

不点击任何按钮,如何直接获取当前位置并将相机移动到该位置。
另外,我发现地图的右上方有一个按钮。单击它时,它将转到当前位置。单击该按钮时如何获取返回的位置?

【问题讨论】:

    标签: android


    【解决方案1】:

    确保您拥有以下权限:

    <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
    <uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"/>
    

    然后进行一些活动并注册一个 LocationListener

    package com.example.location;
    
    import android.content.Context;
    import android.location.Location;
    import android.location.LocationListener;
    import android.location.LocationManager;
    import android.os.Bundle;
    import android.view.View;
    import com.actionbarsherlock.app.SherlockFragmentActivity;
    import com.google.android.gms.maps.CameraUpdate;
    import com.google.android.gms.maps.CameraUpdateFactory;
    import com.google.android.gms.maps.GoogleMap;
    import com.google.android.gms.maps.SupportMapFragment;
    import com.google.android.gms.maps.model.LatLng;
    
    public class LocationActivity extends SherlockFragmentActivity implements LocationListener     {
    private GoogleMap map;
    private LocationManager locationManager;
    private static final long MIN_TIME = 400;
    private static final float MIN_DISTANCE = 1000;
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.map);
        map = ((SupportMapFragment) getSupportFragmentManager().findFragmentById(R.id.map)).getMap();
    
        locationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
        locationManager.requestLocationUpdates(LocationManager.NETWORK_PROVIDER, MIN_TIME, MIN_DISTANCE, this); //You can also use LocationManager.GPS_PROVIDER and LocationManager.PASSIVE_PROVIDER        
    }
    
    @Override
    public void onLocationChanged(Location location) {
        LatLng latLng = new LatLng(location.getLatitude(), location.getLongitude());
        CameraUpdate cameraUpdate = CameraUpdateFactory.newLatLngZoom(latLng, 10);
        map.animateCamera(cameraUpdate);
        locationManager.removeUpdates(this);
    }
    
    @Override
    public void onStatusChanged(String provider, int status, Bundle extras) { }
    
    @Override
    public void onProviderEnabled(String provider) { }
    
    @Override
    public void onProviderDisabled(String provider) { }
    }
    

    map.xml

    <?xml version="1.0" encoding="utf-8"?>
    <fragment xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/map"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    class="com.google.android.gms.maps.SupportMapFragment"/>
    

    【讨论】:

    • 为 removeUpdates() 点赞。
    • 这个 SherlockFragmentActivity 是什么?你的回答中没有提到。
    • 它是一个旧的支持库来支持操作栏...您可以将其替换为 FragmentActivity actionbarsherlock.com
    • 你不需要权限android.permission.ACCESS_COARSE_LOCATION
    • removeupdate() 太棒了,现在地图每 x 秒更新一次 tanxx 时它不会到达当前位置
    【解决方案2】:

    以上答案不是根据 Google Doc 在 Google api v2 中引用的位置跟踪。

    我刚刚按照官方教程完成了这个类,它正在获取当前位置并在我得到它后立即将地图居中。

    您可以扩展此类以使 LocationReciever 具有定期位置更新。 我刚刚在 api 级别 7 上执行了这段代码

    http://developer.android.com/training/location/retrieve-current.html

    来了。

    import android.app.Activity;
    import android.app.Dialog;
    import android.content.Intent;
    import android.content.IntentSender;
    import android.location.Location;
    import android.os.Bundle;
    import android.support.v4.app.DialogFragment;
    import android.support.v4.app.FragmentActivity;
    import android.util.Log;
    import android.widget.Toast;
    
    import com.google.android.gms.common.ConnectionResult;
    import com.google.android.gms.common.GooglePlayServicesClient;
    import com.google.android.gms.common.GooglePlayServicesUtil;
    import com.google.android.gms.location.LocationClient;
    import com.google.android.gms.maps.CameraUpdate;
    import com.google.android.gms.maps.CameraUpdateFactory;
    import com.google.android.gms.maps.GoogleMap;
    import com.google.android.gms.maps.GoogleMap.OnMapLongClickListener;
    import com.google.android.gms.maps.SupportMapFragment;
    import com.google.android.gms.maps.model.LatLng;
    
    
    public class MainActivity extends FragmentActivity implements 
        GooglePlayServicesClient.ConnectionCallbacks, 
        GooglePlayServicesClient.OnConnectionFailedListener{
    
    private SupportMapFragment mapFragment;
    private GoogleMap map;
    private LocationClient mLocationClient;
    /*
     * Define a request code to send to Google Play services
     * This code is returned in Activity.onActivityResult
     */
    private final static int CONNECTION_FAILURE_RESOLUTION_REQUEST = 9000;
    
    // Define a DialogFragment that displays the error dialog
    public static class ErrorDialogFragment extends DialogFragment {
    
        // Global field to contain the error dialog
        private Dialog mDialog;
    
        // Default constructor. Sets the dialog field to null
        public ErrorDialogFragment() {
            super();
            mDialog = null;
        }
    
        // Set the dialog to display
        public void setDialog(Dialog dialog) {
            mDialog = dialog;
        }
    
        // Return a Dialog to the DialogFragment.
        @Override
        public Dialog onCreateDialog(Bundle savedInstanceState) {
            return mDialog;
        }
    }
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main_activity);
    
        mLocationClient = new LocationClient(this, this, this);
    
        mapFragment = ((SupportMapFragment) getSupportFragmentManager().findFragmentById(R.id.map));
        map = mapFragment.getMap();
    
        map.setMyLocationEnabled(true);
    
    }
    
    /*
     * Called when the Activity becomes visible.
     */
    @Override
    protected void onStart() {
        super.onStart();
        // Connect the client.
        if(isGooglePlayServicesAvailable()){
            mLocationClient.connect();
        }
    
    }
    
    /*
     * Called when the Activity is no longer visible.
     */
    @Override
    protected void onStop() {
        // Disconnecting the client invalidates it.
        mLocationClient.disconnect();
        super.onStop();
    }
    
    /*
     * Handle results returned to the FragmentActivity
     * by Google Play services
     */
    @Override
    protected void onActivityResult(
                    int requestCode, int resultCode, Intent data) {
        // Decide what to do based on the original request code
        switch (requestCode) {
    
            case CONNECTION_FAILURE_RESOLUTION_REQUEST:
                /*
                 * If the result code is Activity.RESULT_OK, try
                 * to connect again
                 */
                switch (resultCode) {
                    case Activity.RESULT_OK:
                        mLocationClient.connect();
                        break;
                }
    
        }
    }
    
    private boolean isGooglePlayServicesAvailable() {
        // Check that Google Play services is available
        int resultCode =  GooglePlayServicesUtil.isGooglePlayServicesAvailable(this);
        // If Google Play services is available
        if (ConnectionResult.SUCCESS == resultCode) {
            // In debug mode, log the status
            Log.d("Location Updates", "Google Play services is available.");
            return true;
        } else {
            // Get the error dialog from Google Play services
            Dialog errorDialog = GooglePlayServicesUtil.getErrorDialog( resultCode,
                                                                                                                  this,
                                                                                                                  CONNECTION_FAILURE_RESOLUTION_REQUEST);
    
            // If Google Play services can provide an error dialog
            if (errorDialog != null) {
                // Create a new DialogFragment for the error dialog
                ErrorDialogFragment errorFragment = new ErrorDialogFragment();
                errorFragment.setDialog(errorDialog);
                errorFragment.show(getSupportFragmentManager(), "Location Updates");
            }
    
            return false;
        }
    }
    
    /*
     * Called by Location Services when the request to connect the
     * client finishes successfully. At this point, you can
     * request the current location or start periodic updates
     */
    @Override
    public void onConnected(Bundle dataBundle) {
        // Display the connection status
        Toast.makeText(this, "Connected", Toast.LENGTH_SHORT).show();
        Location location = mLocationClient.getLastLocation();
        LatLng latLng = new LatLng(location.getLatitude(), location.getLongitude());
        CameraUpdate cameraUpdate = CameraUpdateFactory.newLatLngZoom(latLng, 17);
        map.animateCamera(cameraUpdate);
    }
    
    /*
     * Called by Location Services if the connection to the
     * location client drops because of an error.
     */
    @Override
    public void onDisconnected() {
        // Display the connection status
        Toast.makeText(this, "Disconnected. Please re-connect.",
                Toast.LENGTH_SHORT).show();
    }
    
    /*
     * Called by Location Services if the attempt to
     * Location Services fails.
     */
    @Override
    public void onConnectionFailed(ConnectionResult connectionResult) {
        /*
         * Google Play services can resolve some errors it detects.
         * If the error has a resolution, try sending an Intent to
         * start a Google Play services activity that can resolve
         * error.
         */
        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 {
           Toast.makeText(getApplicationContext(), "Sorry. Location services not available to you", Toast.LENGTH_LONG).show();
        }
    }
    
    }
    

    【讨论】:

    • com.google.android.gms.location.LocationClient 在更新 google play 服务后也无法解析..
    • 答案是 2 岁了。如果您可以发布新答案。这会很有帮助
    • 我已经用最新的文档回答了这个问题。请检查一下,
    【解决方案3】:

    我正在解释,如何获取当前位置直接将相机移动到当前位置,假设您已经实现了 ma​​p-v2。 strong> 更多详情,可以参考official doc

    在gradle中添加定位服务

    implementation "com.google.android.gms:play-services-location:11.0.1"
    

    在清单文件中添加位置权限

    <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
    <uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
    

    确保您请求 RunTimePermission。我为此使用Ask-Permission。它易于使用。

    现在参考下面的代码来获取当前位置并将其显示在地图上。

    private FusedLocationProviderClient mFusedLocationProviderClient;
    
    @Override
    public void onCreate(@Nullable Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            mFusedLocationProviderClient = LocationServices
                    .getFusedLocationProviderClient(getActivity());
    
    }
    
    private void getDeviceLocation() {
            try {
                if (mLocationPermissionGranted) {
                    Task<Location> locationResult = mFusedLocationProviderClient.getLastLocation();
                    locationResult.addOnCompleteListener(new OnCompleteListener<Location>() {
                        @Override
                        public void onComplete(@NonNull Task<Location> task) {
                            if (task.isSuccessful()) {
                                // Set the map's camera position to the current location of the device.
                                Location location = task.getResult();
                                LatLng currentLatLng = new LatLng(location.getLatitude(),
                                        location.getLongitude());
                                CameraUpdate update = CameraUpdateFactory.newLatLngZoom(currentLatLng,
                                        DEFAULT_ZOOM);
                                googleMap.moveCamera(update);
                            }
                        }
                    });
                }
            } catch (SecurityException e) {
                Log.e("Exception: %s", e.getMessage());
            }
    }
    

    当用户授予定位权限时调用上述getDeviceLocation()方法

    private void updateLocationUI() {
            if (googleMap == null) {
                return;
            }
            try {
                if (mLocationPermissionGranted) {
                    googleMap.setMyLocationEnabled(true);
                    googleMap.getUiSettings().setMyLocationButtonEnabled(true);
                    getDeviceLocation();
                } else {
                    googleMap.setMyLocationEnabled(false);
                    googleMap.getUiSettings().setMyLocationButtonEnabled(false);
                }
            } catch (SecurityException e) {
                Log.e("Exception: %s", e.getMessage());
            }
        }
    

    【讨论】:

      【解决方案4】:

      只需将 moveCamera 更改为 animateCamera 如下所示

      Googlemap.animateCamera(CameraUpdateFactory.newLatLngZoom(locate, 16F))
      

      【讨论】:

        【解决方案5】:

        我的答案是针对那些在应用启动时正在寻找当前位置缩放动画的人。并获取当前位置的位置。

        如果有任何遗漏,请在评论中告诉我。

        注意:-假设您已授予所有运行时权限位置。

        @Override
        public void onMapReady(GoogleMap googleMap) {
            MapsInitializer.initialize(this);
            mMap = googleMap;
            
            getData(mMap);
            animateCamera();
        
        
        }
        

        getData 方法返回地图中理想位置的 lat lng。所以基本上最后相机缩放动画在当前位置变得理想。所以它给出了当前位置 lat lng。

          private void getData(GoogleMap mMap) {
        
            mMap.setOnCameraIdleListener(new GoogleMap.OnCameraIdleListener() {
                @Override
                public void onCameraIdle() {
        
                    LatLng center = mMap.getCameraPosition().target;
                    String sLatitude = String.format("%.6f", center.latitude);
                    String sLongitude = String.format("%.6f", center.longitude);
                    StringBuilder mLatLng = new StringBuilder();
                    mLatLng.append(sLatitude);
                    mLatLng.append("°");
                    mLatLng.append(" ");
                    mLatLng.append(sLongitude);
                    mLatLng.append("°");
                    binding.latLng.setText(mLatLng);
        
                }
            });
        
        private void animateCamera() {
            Location location = getLastKnownLocation();
            if (location != null) {
        
                mMap.setMyLocationEnabled(true);
                mMap.getUiSettings().setMyLocationButtonEnabled(true);
                mMap.getUiSettings().setAllGesturesEnabled(true);
                //delay is for after map loaded animation starts
                Handler handler = new Handler();
                handler.postDelayed(new Runnable() {
                    @Override
                    public void run() {
                        mMap.animateCamera(CameraUpdateFactory.newLatLngZoom(new LatLng(location.getLatitude(), location.getLongitude()), 15));
        
                    }
                }, 2000);
            }
        }
        

        这将返回最佳位置提供者

        private Location getLastKnownLocation() {
            locationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
            List<String> providers = locationManager.getProviders(true);
            Location bestLocation = null;
            for (String provider : providers) {
                @SuppressLint("MissingPermission") Location l = locationManager.getLastKnownLocation(provider);
                if (l == null) {
                    continue;
                }
                if (bestLocation == null || l.getAccuracy() < bestLocation.getAccuracy()) {
                    // Found best last known location: %s", l);
                    bestLocation = l;
                }
            }
            return bestLocation;
        }
        

        【讨论】:

          猜你喜欢
          • 2018-09-13
          • 2015-03-13
          • 2021-10-09
          • 2012-11-30
          • 1970-01-01
          • 2013-08-27
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多