Search code examples
javaandroiddictionaryarea

How to spawn markers on android map inside a circular range


I'm trying to make a pokemonGo style application. I have tried using latitude and longitude formulas to calculate the range of coordinates where markers (pokemon) should spawn but I only managed to get a rectangular area. I would like to spawn them on a circular area around the player, how can I do that?

Here is the code where I calculated the rectangular area.

        Random r = new Random();
        int randomDistanceLatitude = r.nextInt(range*2) - range;
        r = new Random();
        int randomDistanceLongitude = r.nextInt(range*2) - range;


        double latitudeDegreeToAdd = 1.7 * randomDistanceLatitude * 0.000009043717329571146924;
        double longitudeDegreeToAdd = randomDistanceLongitude * (1 / (111320 * Math.cos(infoLocal.getLastKnownLocation().getLatitude())));

        LatLng enemy1Location = new LatLng(infoLocal.getLastKnownLocation().getLatitude() + latitudeDegreeToAdd, infoLocal.getLastKnownLocation().getLongitude() + longitudeDegreeToAdd);

        enemies[i] = mMap.addMarker(new MarkerOptions().position(enemy1Location).title("Monster").snippet("Click to Attack!").icon(BitmapDescriptorFactory.fromResource(R.drawable.enemy3)).anchor(0.5f, 0.5f));

Solution

  • It seems to be a math question.

    Circle's formula is (x, y) = (cos(angle) * rX, sin(angle) * rY) + (centerX, centerY)

    So, code will be look like this.

    Random r = new Random();
    double radius = r.nextFloat() * range; // or r.nextDouble()...
    double angle = r.nextFloat() * 2.0f * Math.PI;
    double randomDistanceLatitude = Math.cos(angle) * radius;
    double randomDistanceLongitude = Math.sin(angle) * radius;
    ...
    

    As lat lng is not in cartesian coordinate system, it's not a pure circle, but range is enough small in this use case to ignore such distortion, I think.


    Additional notes.

    If mMap means Google Maps map, you may have interests in Google Maps - Shape - Circle