How to know which Marker was clicked on Google Maps v2 for Android?

六眼飞鱼酱① 提交于 2019-11-28 09:14:30

In reply to:

The question is: How do I identify what entity the clicked Marker 'marker' represents? [...] There's also a marker.getId(), but such ID is generated by the API and I can't control it

You can control it. The marker is returned by addMarker(), so you can get its ID and store it. Here's the code:

Map <String, Integer> markers = new HashMap<String, Integer>();

...

MarkerOptions mo = new MarkerOptions()
.icon(BitmapDescriptorFactory.fromResource(R.drawable.my_marker))
.position(new LatLng(mLat, mLon))
.flat(true) 
.snippet("Click here for details")
.rotation(0)
.title(title);

When you add the marker to the map, store its ID on the container

MyClass myObject = new MyClass(lat, lon); // The class that you are rendering on the map with Markers, for example "Monument"
Marker mkr = map.addMarker(mo);
markers.put(mkr.getId(), myObject.getId()); 

Then when the marker is clicked, you can recover the id of "myObject" like this

map.setOnInfoWindowClickListener(new OnInfoWindowClickListener() {
    public void onInfoWindowClick(Marker marker) {
        int id = markers.get(marker.getId());
        // Now id contains which Monument (or your preferred class) was clicked                         
    }
});

There is a better option, and this is what google suggests:

Tag : An Object associated with the marker. For example, the Object can contain data about what the marker represents. This is easier than storing a separate Map<Marker, Object>. As another example, you can associate a String ID corresponding to the ID from a data set. Google Maps Android API neither reads nor writes this property.

Source

So you can do something like this:

for (ListItem it: mList) {
    Marker mk = mMap.addMarker(new MarkerOptions().position(it.getLatLng()).title(it.getName()).snippet(it.getAddress()));
    mk.setTag(it.getID());
}

mMap.setOnMarkerClickListener(new GoogleMap.OnMarkerClickListener() {
    @Override
    public boolean onMarkerClick(Marker marker) {
        Integer id = (Integer) marker.getTag();
        return false;
    }
});

You are not obligated to show title when you have it set, so you can use that and as long as you return a View from getInfoContents and not setText on any subview of that returned View with title value.

Depending on how and if you already keep references to all markers, there are alternatives, e.g. if you had List<Marker> policeMarkers and List<Marker> badGuysMarkers you can use a conditional if (policeMarkers.contains(marker)) { ... } else { ... }.

You can also keep a Map<Marker, YourMarkerRelatedDataModel> allMarkers and do YourMarkerRelatedDataModel model = allMarkers.get(marker); and use that value to differentiate.

Finally you can use Android Maps Extensions, which adds functions like Marker.setData(Object) and Object Marker.getData() to keep your model close to your markers and not create things like Map<Marker, Model>.

try this code:

@Override
    public void onInfoWindowClick(final Marker marker) 
    {
        // TODO Auto-generated method stub
       if (marker.getTitle().equalsIgnoreCase("Start")) {
        Toast.makeText(showMaps.this, "You have click on start -->",
                Toast.LENGTH_LONG).show();
        Log.e("marker.getPosition()-->", "" + marker.getPosition());
      }
    }
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!