Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Android Google Maps: How to get the area which is currently shown in screen device?

Is there a way to get the coordinates of the current area, which is shown at the device?

Background is, we want to show "nearby" places, which are stored in our own database. So let's say, the user looks at following clip of a map:

enter image description here

How do we get the longitude/latitude of the screen (or the point in the middle of the screen and a radius which covers everything?). Please keep in mind, center of the map is not usually the current position, since the user can move the center of the card!

like image 870
longi Avatar asked Apr 17 '13 09:04

longi


3 Answers

Use map.getProjection().getVisibleRegion(). From VisibleRegion you can get LatLngBounds, which is easy to work with. You may also try directly with the region, which might be trapezoid.

like image 132
MaciejGórski Avatar answered Nov 20 '22 14:11

MaciejGórski


I found the solution for Google Map API v2 from few of responses:

stackoverflow#1 and stackoverflow#2

So, need implements Activity from GoogleMap.OnCameraChangeListener interface


    private static final int REQUEST_CODE_GOOGLE_PLAY_SERVECES_ERROR = -1;
    private static final double EARTH_RADIOUS = 3958.75; // Earth radius;
    private static final int METER_CONVERSION = 1609;
    private GoogleMap mGoogleMap;

    @Override
    protected void onCreate(Bundle savedInstanceState)
    {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_layout);

        int status = GooglePlayServicesUtil.isGooglePlayServicesAvailable(mContext);
        if (status != ConnectionResult.SUCCESS)
        {
            Dialog dialog = GooglePlayServicesUtil.getErrorDialog(status, activity,
                    REQUEST_CODE_GOOGLE_PLAY_SERVECES_ERROR);
            dialog.show();
            mGoogleMap = null;
        }
        else
        {
            mGoogleMap = ((SupportMapFragment) getFragmentManager().findFragmentById(
                    R.id.fragment_shops_layout_maps_fragment)).getMap();

            mGoogleMap.setOnCameraChangeListener(this);
        }
    }

The listener, that working when map scaled. Determin as LatLng the positions of bottom left, bottom right, top left and top right sides of map, that showing on screen. By greatest side of screen and two points we can get radius from center of map.

    @Override
    public void onCameraChange(CameraPosition cameraPosition)
    {
        // Listener of zooming;
        float zoomLevel = cameraPosition.zoom;
        VisibleRegion visibleRegion = mGoogleMap.getProjection().getVisibleRegion();
        LatLng nearLeft = visibleRegion.nearLeft;
        LatLng nearRight = visibleRegion.nearRight;
        LatLng farLeft = visibleRegion.farLeft;
        LatLng farRight = visibleRegion.farRight;
        double dist_w = distanceFrom(nearLeft.latitude, nearLeft.longitude, nearRight.latitude, nearRight.longitude);
        double dist_h = distanceFrom(farLeft.latitude, farLeft.longitude, farRight.latitude, farRight.longitude);
        Log.d("DISTANCE: ", "DISTANCE WIDTH: " + dist_w + " DISTANCE HEIGHT: " + dist_h);
    }

Return distance between 2 points, stored as 2 pair location at meters;

    public double distanceFrom(double lat1, double lng1, double lat2, double lng2)
    {
        // Return distance between 2 points, stored as 2 pair location;
        double dLat = Math.toRadians(lat2 - lat1);
        double dLng = Math.toRadians(lng2 - lng1);
        double a = Math.sin(dLat / 2) * Math.sin(dLat / 2) + Math.cos(Math.toRadians(lat1))
                * Math.cos(Math.toRadians(lat2)) * Math.sin(dLng / 2) * Math.sin(dLng / 2);
        double c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a));
        double dist = EARTH_RADIOUS * c;
        return new Double(dist * METER_CONVERSION).floatValue();
    }

If you want get radius of area, that showed on screen just need devided by 2.

I hope will useful !

like image 12
cosic Avatar answered Nov 20 '22 13:11

cosic


This calculates the radio in km based on the map width:

public double calculateVisibleRadius() {
    float[] distanceWidth = new float[1];
    VisibleRegion visibleRegion = map.getProjection().getVisibleRegion();
    LatLng farRight = visibleRegion.farRight;
    LatLng farLeft = visibleRegion.farLeft;
    LatLng nearRight = visibleRegion.nearRight;
    LatLng nearLeft = visibleRegion.nearLeft;
    //calculate the distance between left <-> right of map on screen
    Location.distanceBetween( (farLeft.latitude + nearLeft.latitude) / 2, farLeft.longitude, (farRight.latitude + nearRight.latitude) / 2, farRight.longitude, distanceWidth );
    // visible radius is / 2  and /1000 in Km:
     return distanceWidth[0] / 2 / 1000 ;
}
like image 3
Khaleesi Avatar answered Nov 20 '22 13:11

Khaleesi